1fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck/* 2fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * Copyright (C) 2014 The Android Open Source Project 3fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * 4fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * Licensed under the Apache License, Version 2.0 (the "License"); 5fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * you may not use this file except in compliance with the License. 6fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * You may obtain a copy of the License at 7fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * 8fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * http://www.apache.org/licenses/LICENSE-2.0 9fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * 10fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * Unless required by applicable law or agreed to in writing, software 11fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * distributed under the License is distributed on an "AS IS" BASIS, 12fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * See the License for the specific language governing permissions and 14fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck * limitations under the License. 15fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck */ 16fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#include "DrawProfiler.h" 17fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 18fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#include <cutils/compiler.h> 19fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 20fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#include "OpenGLRenderer.h" 21fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#include "Properties.h" 22fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 23fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define DEFAULT_MAX_FRAMES 128 24fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 2523d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck#define RETURN_IF_PROFILING_DISABLED() if (CC_LIKELY(mType == kNone)) return 2623d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck#define RETURN_IF_DISABLED() if (CC_LIKELY(mType == kNone && !mShowDirtyRegions)) return 27fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 28fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define NANOS_TO_MILLIS_FLOAT(nanos) ((nanos) * 0.000001f) 29fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 30fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define PROFILE_DRAW_WIDTH 3 31fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define PROFILE_DRAW_THRESHOLD_STROKE_WIDTH 2 32fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define PROFILE_DRAW_DP_PER_MS 7 33fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 34fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck// Number of floats we want to display from FrameTimingData 35fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck// If this is changed make sure to update the indexes below 36fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define NUM_ELEMENTS 4 37fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 38fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define RECORD_INDEX 0 39fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define PREPARE_INDEX 1 40fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define PLAYBACK_INDEX 2 41fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define SWAPBUFFERS_INDEX 3 42fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 43fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck// Must be NUM_ELEMENTS in size 44fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckstatic const SkColor ELEMENT_COLORS[] = { 0xcf3e66cc, 0xcf8f00ff, 0xcfdc3912, 0xcfe69800 }; 45fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckstatic const SkColor CURRENT_FRAME_COLOR = 0xcf5faa4d; 46fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckstatic const SkColor THRESHOLD_COLOR = 0xff5faa4d; 47fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 48fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck// We could get this from TimeLord and use the actual frame interval, but 49fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck// this is good enough 50fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck#define FRAME_THRESHOLD 16 51fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 52fe5e7b7346a54537b980796ceeca66bfdbd05561John Recknamespace android { 53fe5e7b7346a54537b980796ceeca66bfdbd05561John Recknamespace uirenderer { 54fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 55fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckstatic int dpToPx(int dp, float density) { 56fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck return (int) (dp * density + 0.5f); 57fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 58fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 59fe5e7b7346a54537b980796ceeca66bfdbd05561John ReckDrawProfiler::DrawProfiler() 60fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck : mType(kNone) 61fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck , mDensity(0) 62fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck , mData(NULL) 63fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck , mDataSize(0) 64fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck , mCurrentFrame(-1) 65fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck , mPreviousTime(0) 66fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck , mVerticalUnit(0) 67fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck , mHorizontalUnit(0) 6823d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck , mThresholdStroke(0) 6923d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck , mShowDirtyRegions(false) 7023d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck , mFlashToggle(false) { 71fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck setDensity(1); 72fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 73fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 74fe5e7b7346a54537b980796ceeca66bfdbd05561John ReckDrawProfiler::~DrawProfiler() { 75fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck destroyData(); 76fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 77fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 78fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::setDensity(float density) { 79fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck if (CC_UNLIKELY(mDensity != density)) { 80fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mDensity = density; 81fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mVerticalUnit = dpToPx(PROFILE_DRAW_DP_PER_MS, density); 82fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mHorizontalUnit = dpToPx(PROFILE_DRAW_WIDTH, density); 83fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mThresholdStroke = dpToPx(PROFILE_DRAW_THRESHOLD_STROKE_WIDTH, density); 84fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } 85fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 86fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 87fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::startFrame(nsecs_t recordDurationNanos) { 8823d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck RETURN_IF_PROFILING_DISABLED(); 89fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mData[mCurrentFrame].record = NANOS_TO_MILLIS_FLOAT(recordDurationNanos); 90fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mPreviousTime = systemTime(CLOCK_MONOTONIC); 91fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 92fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 93fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::markPlaybackStart() { 9423d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck RETURN_IF_PROFILING_DISABLED(); 95fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck nsecs_t now = systemTime(CLOCK_MONOTONIC); 96fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mData[mCurrentFrame].prepare = NANOS_TO_MILLIS_FLOAT(now - mPreviousTime); 97fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mPreviousTime = now; 98fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 99fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 100fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::markPlaybackEnd() { 10123d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck RETURN_IF_PROFILING_DISABLED(); 102fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck nsecs_t now = systemTime(CLOCK_MONOTONIC); 103fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mData[mCurrentFrame].playback = NANOS_TO_MILLIS_FLOAT(now - mPreviousTime); 104fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mPreviousTime = now; 105fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 106fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 107fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::finishFrame() { 10823d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck RETURN_IF_PROFILING_DISABLED(); 109fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck nsecs_t now = systemTime(CLOCK_MONOTONIC); 110fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mData[mCurrentFrame].swapBuffers = NANOS_TO_MILLIS_FLOAT(now - mPreviousTime); 111fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mPreviousTime = now; 112fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mCurrentFrame = (mCurrentFrame + 1) % mDataSize; 113fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 114fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 115e4267ea4f20740c37c01bfb6aefcf61fddc4566aJohn Reckvoid DrawProfiler::unionDirty(SkRect* dirty) { 116fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck RETURN_IF_DISABLED(); 117fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck // Not worth worrying about minimizing the dirty region for debugging, so just 118fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck // dirty the entire viewport. 119fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck if (dirty) { 12023d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck mDirtyRegion = *dirty; 121fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck dirty->setEmpty(); 122fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } 123fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 124fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 125fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::draw(OpenGLRenderer* canvas) { 12623d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck RETURN_IF_DISABLED(); 12723d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck 12823d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck if (mShowDirtyRegions) { 12923d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck mFlashToggle = !mFlashToggle; 13023d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck if (mFlashToggle) { 13123d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck SkPaint paint; 13223d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck paint.setColor(0x7fff0000); 13323d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck canvas->drawRect(mDirtyRegion.fLeft, mDirtyRegion.fTop, 13423d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck mDirtyRegion.fRight, mDirtyRegion.fBottom, &paint); 13523d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck } 136fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } 137fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 13823d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck if (mType == kBars) { 13923d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck prepareShapes(canvas->getViewportHeight()); 14023d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck drawGraph(canvas); 14123d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck drawCurrentFrame(canvas); 14223d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck drawThreshold(canvas); 14323d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck } 144fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 145fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 146fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::createData() { 147fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck if (mData) return; 148fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 149fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mDataSize = property_get_int32(PROPERTY_PROFILE_MAXFRAMES, DEFAULT_MAX_FRAMES); 150fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck if (mDataSize <= 0) mDataSize = 1; 151fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck if (mDataSize > 4096) mDataSize = 4096; // Reasonable maximum 152fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mData = (FrameTimingData*) calloc(mDataSize, sizeof(FrameTimingData)); 153fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mRects = new float*[NUM_ELEMENTS]; 154fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck for (int i = 0; i < NUM_ELEMENTS; i++) { 155fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck // 4 floats per rect 156fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mRects[i] = (float*) calloc(mDataSize, 4 * sizeof(float)); 157fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } 158fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mCurrentFrame = 0; 159fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 160fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 161fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::destroyData() { 162fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck delete mData; 163fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mData = NULL; 164fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 165fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 166fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::addRect(Rect& r, float data, float* shapeOutput) { 167fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck r.top = r.bottom - (data * mVerticalUnit); 168fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck shapeOutput[0] = r.left; 169fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck shapeOutput[1] = r.top; 170fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck shapeOutput[2] = r.right; 171fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck shapeOutput[3] = r.bottom; 172fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck r.bottom = r.top; 173fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 174fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 175fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::prepareShapes(const int baseline) { 176fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck Rect r; 177fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck r.right = mHorizontalUnit; 178fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck for (int i = 0; i < mDataSize; i++) { 179fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck const int shapeIndex = i * 4; 180fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck r.bottom = baseline; 181fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck addRect(r, mData[i].record, mRects[RECORD_INDEX] + shapeIndex); 182fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck addRect(r, mData[i].prepare, mRects[PREPARE_INDEX] + shapeIndex); 183fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck addRect(r, mData[i].playback, mRects[PLAYBACK_INDEX] + shapeIndex); 184fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck addRect(r, mData[i].swapBuffers, mRects[SWAPBUFFERS_INDEX] + shapeIndex); 185fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck r.translate(mHorizontalUnit, 0); 186fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } 187fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 188fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 189fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::drawGraph(OpenGLRenderer* canvas) { 190fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck SkPaint paint; 191fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck for (int i = 0; i < NUM_ELEMENTS; i++) { 192fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck paint.setColor(ELEMENT_COLORS[i]); 193fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck canvas->drawRects(mRects[i], mDataSize * 4, &paint); 194fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } 195fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 196fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 197fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::drawCurrentFrame(OpenGLRenderer* canvas) { 198fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck // This draws a solid rect over the entirety of the current frame's shape 199fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck // To do so we use the bottom of mRects[0] and the top of mRects[NUM_ELEMENTS-1] 200fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck // which will therefore fully overlap the previously drawn rects 201fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck SkPaint paint; 202fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck paint.setColor(CURRENT_FRAME_COLOR); 203fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck const int i = mCurrentFrame * 4; 204fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck canvas->drawRect(mRects[0][i], mRects[NUM_ELEMENTS-1][i+1], mRects[0][i+2], 205fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mRects[0][i+3], &paint); 206fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 207fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 208fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::drawThreshold(OpenGLRenderer* canvas) { 209fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck SkPaint paint; 210fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck paint.setColor(THRESHOLD_COLOR); 211fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck paint.setStrokeWidth(mThresholdStroke); 212fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 213fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck float pts[4]; 214fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck pts[0] = 0.0f; 215fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck pts[1] = pts[3] = canvas->getViewportHeight() - (FRAME_THRESHOLD * mVerticalUnit); 216fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck pts[2] = canvas->getViewportWidth(); 217fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck canvas->drawLines(pts, 4, &paint); 218fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 219fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 220fe5e7b7346a54537b980796ceeca66bfdbd05561John ReckDrawProfiler::ProfileType DrawProfiler::loadRequestedProfileType() { 221fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck ProfileType type = kNone; 222fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck char buf[PROPERTY_VALUE_MAX] = {'\0',}; 223fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck if (property_get(PROPERTY_PROFILE, buf, "") > 0) { 224fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck if (!strcmp(buf, PROPERTY_PROFILE_VISUALIZE_BARS)) { 225fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck type = kBars; 226fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } else if (!strcmp(buf, "true")) { 227fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck type = kConsole; 228fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } 229fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } 230fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck return type; 231fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 232fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 233fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckbool DrawProfiler::loadSystemProperties() { 23423d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck bool changed = false; 235fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck ProfileType newType = loadRequestedProfileType(); 236fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck if (newType != mType) { 237fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mType = newType; 238fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck if (mType == kNone) { 239fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck destroyData(); 240fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } else { 241fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck createData(); 242fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } 24323d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck changed = true; 244fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } 24523d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck bool showDirty = property_get_bool(PROPERTY_DEBUG_SHOW_DIRTY_REGIONS, false); 24623d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck if (showDirty != mShowDirtyRegions) { 24723d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck mShowDirtyRegions = showDirty; 24823d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck changed = true; 24923d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck } 25023d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck return changed; 251fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 252fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 253fe5e7b7346a54537b980796ceeca66bfdbd05561John Reckvoid DrawProfiler::dumpData(int fd) { 25423d307c8d88f4a3849163b9e5b7cd11d0d4f372cJohn Reck RETURN_IF_PROFILING_DISABLED(); 255fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 256fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck // This method logs the last N frames (where N is <= mDataSize) since the 257fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck // last call to dumpData(). In other words if there's a dumpData(), draw frame, 258fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck // dumpData(), the last dumpData() should only log 1 frame. 259fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 260fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck const FrameTimingData emptyData = {0, 0, 0, 0}; 261fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 262fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck FILE *file = fdopen(fd, "a"); 263fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck fprintf(file, "\n\tDraw\tPrepare\tProcess\tExecute\n"); 264fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 265fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck for (int frameOffset = 1; frameOffset <= mDataSize; frameOffset++) { 266fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck int i = (mCurrentFrame + frameOffset) % mDataSize; 267fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck if (!memcmp(mData + i, &emptyData, sizeof(FrameTimingData))) { 268fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck continue; 269fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } 270fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck fprintf(file, "\t%3.2f\t%3.2f\t%3.2f\t%3.2f\n", 271fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mData[i].record, mData[i].prepare, mData[i].playback, mData[i].swapBuffers); 272fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck } 273fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck // reset the buffer 274fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck memset(mData, 0, sizeof(FrameTimingData) * mDataSize); 275fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck mCurrentFrame = 0; 276fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 277fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck fflush(file); 278fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} 279fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck 280fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} /* namespace uirenderer */ 281fe5e7b7346a54537b980796ceeca66bfdbd05561John Reck} /* namespace android */ 282