157 lines
5.6 KiB
C
157 lines
5.6 KiB
C
|
/*
|
||
|
* Copyright (C) 2009 The Android Open Source Project
|
||
|
* All rights reserved.
|
||
|
*
|
||
|
* Redistribution and use in source and binary forms, with or without
|
||
|
* modification, are permitted provided that the following conditions
|
||
|
* are met:
|
||
|
* * Redistributions of source code must retain the above copyright
|
||
|
* notice, this list of conditions and the following disclaimer.
|
||
|
* * Redistributions in binary form must reproduce the above copyright
|
||
|
* notice, this list of conditions and the following disclaimer in
|
||
|
* the documentation and/or other materials provided with the
|
||
|
* distribution.
|
||
|
*
|
||
|
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||
|
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||
|
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
|
||
|
* FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
|
||
|
* COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
|
||
|
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||
|
* BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
|
||
|
* OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
|
||
|
* AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||
|
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
|
||
|
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||
|
* SUCH DAMAGE.
|
||
|
*/
|
||
|
|
||
|
#ifndef ANDROID_NATIVETEST_SYSTEM_EXTRAS_TESTS_SDCARD_STOPWATCH_H_
|
||
|
#define ANDROID_NATIVETEST_SYSTEM_EXTRAS_TESTS_SDCARD_STOPWATCH_H_
|
||
|
|
||
|
#include <stdlib.h>
|
||
|
#include <stdio.h>
|
||
|
#include <time.h>
|
||
|
|
||
|
namespace android_test {
|
||
|
|
||
|
// StopWatch class to collect execution statistics.
|
||
|
//
|
||
|
// Once the watch has been created, start and stop can be called to
|
||
|
// capture an event duration.
|
||
|
//
|
||
|
// On completion, use 'sprint' to retrieve the data.
|
||
|
//
|
||
|
// If StopWatch::setPrintRawMode(true) has been called, the raw
|
||
|
// samples also are printed.
|
||
|
// The print method is thread safe to avoid mixing the result of
|
||
|
// watches on different threads. For processes, use different files
|
||
|
// that you concat after the run.
|
||
|
//
|
||
|
// If the time measure is associated with some volume of data, use
|
||
|
// setMbytes, the print method will compute the average throughput
|
||
|
// based on that value.
|
||
|
//
|
||
|
// To capture the time accurately and since the runs are not too long,
|
||
|
// we collect the raw start and stop time in an array that get
|
||
|
// processed once all the measurements have been done.
|
||
|
//
|
||
|
// Typical Usage:
|
||
|
// ==============
|
||
|
//
|
||
|
// StopWatch watch("my name", 20);
|
||
|
//
|
||
|
// for (int i = 0; i < 20; ++i) {
|
||
|
// watch.start();
|
||
|
// doMyStuff();
|
||
|
// watch.stop();
|
||
|
// }
|
||
|
// char buffer[4096];
|
||
|
// char *str = buffer;
|
||
|
// size_t size = sizeof(buffer);
|
||
|
// watch.sprint(&str, &size);
|
||
|
//
|
||
|
|
||
|
class StopWatch {
|
||
|
public:
|
||
|
// Time of the snapshot and its nature (start of the interval or end of it).
|
||
|
struct Measurement {
|
||
|
struct timespec mTime;
|
||
|
bool mIsStart;
|
||
|
};
|
||
|
static const size_t kUseDefaultCapacity = 20;
|
||
|
|
||
|
// Create a stop watch. Default capacity == 2 * interval_nb
|
||
|
// @param name To be used when the results are displayed. No
|
||
|
// spaces, use _ instead.
|
||
|
// @param capacity Hint about the number of sampless that will be
|
||
|
// measured (1 sample == 1 start + 1 stop). Used
|
||
|
// to size the internal storage, when the capacity
|
||
|
// is reached, it is doubled.
|
||
|
StopWatch(const char *name, size_t capacity = kUseDefaultCapacity);
|
||
|
~StopWatch();
|
||
|
|
||
|
// A StopWatch instance measures time intervals. Use setDataSize
|
||
|
// if some volume of data is processed during these intervals, to
|
||
|
// get the average throughput (in kbytes/s) printed.
|
||
|
void setDataSize(size_t size_in_bytes) { mSizeKbytes = size_in_bytes / 1000; }
|
||
|
|
||
|
// Starts and stops the timer. The time between the 2 calls is an
|
||
|
// interval whose duration will be reported in sprint.
|
||
|
void start();
|
||
|
void stop();
|
||
|
|
||
|
// Print a summary of the measurement and optionaly the raw data.
|
||
|
// The summary is commented out using a leading '#'. The raw data
|
||
|
// is a pair (time, duration). The 1st sample is always at time
|
||
|
// '0.0'.
|
||
|
// @param str[inout] On entry points to the begining of a buffer
|
||
|
// where to write the data. On exit points pass the last byte
|
||
|
// written.
|
||
|
// @param size[inout] On entry points to the size of the buffer
|
||
|
// pointed by *str. On exit *size is the amount of free space left
|
||
|
// in the buffer. If there was not enough space the data is truncated
|
||
|
// and a warning is printed.
|
||
|
void sprint(char **str, size_t *size);
|
||
|
|
||
|
// @return true if at least one interval was timed.
|
||
|
bool used() const { return mUsed; }
|
||
|
|
||
|
// Affects all the timers. Instructs all the timers to print the
|
||
|
// raw data as well as the summary.
|
||
|
static void setPrintRawMode(bool printRaw);
|
||
|
|
||
|
private:
|
||
|
void checkCapacity();
|
||
|
double timespecToDouble(const struct timespec& time);
|
||
|
void printAverageMinMax(char **str, size_t *size);
|
||
|
void printThroughput(char **str, size_t *size);
|
||
|
// Allocate mDeltas and fill it in. Search for the min and max.
|
||
|
void processSamples();
|
||
|
|
||
|
char *const mName; // Name of the test.
|
||
|
struct timespec mStart;
|
||
|
size_t mNum; // # of intervals == # of start() calls.
|
||
|
struct Measurement *mData;
|
||
|
size_t mDataLen;
|
||
|
size_t mCapacity;
|
||
|
int mSizeKbytes;
|
||
|
|
||
|
bool mAlreadyPrinted;
|
||
|
bool mPrintRaw;
|
||
|
|
||
|
double mDuration;
|
||
|
double mDeviation;
|
||
|
double mMinDuration;
|
||
|
size_t mMinIdx;
|
||
|
double mMaxDuration;
|
||
|
size_t mMaxIdx;
|
||
|
double *mDeltas;
|
||
|
|
||
|
bool mUsed;
|
||
|
};
|
||
|
|
||
|
} // namespace android_test
|
||
|
|
||
|
#endif // ANDROID_NATIVETEST_SYSTEM_EXTRAS_TESTS_SDCARD_STOPWATCH_H_
|