summaryrefslogtreecommitdiffstats
path: root/opengl
diff options
context:
space:
mode:
authorSiva Velusamy <vsiva@google.com>2012-01-03 14:39:31 -0800
committerSiva Velusamy <vsiva@google.com>2012-01-04 12:50:13 -0800
commit157fea642cb4c10e44a61f932c68f7c3a2610a81 (patch)
tree58badbc40683dde6329be8f8560259afc6180e66 /opengl
parent193b45970e512e99b4557fe4bbb30b2dca30320f (diff)
downloadframeworks_base-157fea642cb4c10e44a61f932c68f7c3a2610a81.zip
frameworks_base-157fea642cb4c10e44a61f932c68f7c3a2610a81.tar.gz
frameworks_base-157fea642cb4c10e44a61f932c68f7c3a2610a81.tar.bz2
gltrace: add user settings to control data captured.
Currently users do not have control over the amount of data captured during tracing. This patch adds 3 settings that users can enable/disable at runtime: - capture framebuffer on eglSwap() calls - capture framebuffer on glDraw*() calls - capture texture data passed to glTexImage*() calls Disabling these options when not needed signficantly decreases the size of the trace file, and reduces performance overhead for the running application. These settings are stored in the per process GLTraceState. A separate thread listens for commands from the host, and updates the state based on the user commands. Change-Id: Ic4518b94e8bcbc5330ac7138153721caa98b365d
Diffstat (limited to 'opengl')
-rw-r--r--opengl/libs/GLES_trace/src/gltrace_context.cpp51
-rw-r--r--opengl/libs/GLES_trace/src/gltrace_context.h28
-rw-r--r--opengl/libs/GLES_trace/src/gltrace_egl.cpp6
-rw-r--r--opengl/libs/GLES_trace/src/gltrace_eglapi.cpp44
-rw-r--r--opengl/libs/GLES_trace/src/gltrace_fixup.cpp14
5 files changed, 135 insertions, 8 deletions
diff --git a/opengl/libs/GLES_trace/src/gltrace_context.cpp b/opengl/libs/GLES_trace/src/gltrace_context.cpp
index 81d2f1a..65b7662 100644
--- a/opengl/libs/GLES_trace/src/gltrace_context.cpp
+++ b/opengl/libs/GLES_trace/src/gltrace_context.cpp
@@ -59,6 +59,11 @@ void releaseContext() {
GLTraceState::GLTraceState(TCPStream *stream) {
mTraceContextIds = 0;
mStream = stream;
+
+ mCollectFbOnEglSwap = false;
+ mCollectFbOnGlDraw = false;
+ mCollectTextureDataOnGlTexImage = false;
+ pthread_rwlock_init(&mTraceOptionsRwLock, NULL);
}
GLTraceState::~GLTraceState() {
@@ -72,12 +77,49 @@ TCPStream *GLTraceState::getStream() {
return mStream;
}
+void GLTraceState::safeSetValue(bool *ptr, bool value, pthread_rwlock_t *lock) {
+ pthread_rwlock_wrlock(lock);
+ *ptr = value;
+ pthread_rwlock_unlock(lock);
+}
+
+bool GLTraceState::safeGetValue(bool *ptr, pthread_rwlock_t *lock) {
+ pthread_rwlock_rdlock(lock);
+ bool value = *ptr;
+ pthread_rwlock_unlock(lock);
+ return value;
+}
+
+void GLTraceState::setCollectFbOnEglSwap(bool en) {
+ safeSetValue(&mCollectFbOnEglSwap, en, &mTraceOptionsRwLock);
+}
+
+void GLTraceState::setCollectFbOnGlDraw(bool en) {
+ safeSetValue(&mCollectFbOnGlDraw, en, &mTraceOptionsRwLock);
+}
+
+void GLTraceState::setCollectTextureDataOnGlTexImage(bool en) {
+ safeSetValue(&mCollectTextureDataOnGlTexImage, en, &mTraceOptionsRwLock);
+}
+
+bool GLTraceState::shouldCollectFbOnEglSwap() {
+ return safeGetValue(&mCollectFbOnEglSwap, &mTraceOptionsRwLock);
+}
+
+bool GLTraceState::shouldCollectFbOnGlDraw() {
+ return safeGetValue(&mCollectFbOnGlDraw, &mTraceOptionsRwLock);
+}
+
+bool GLTraceState::shouldCollectTextureDataOnGlTexImage() {
+ return safeGetValue(&mCollectTextureDataOnGlTexImage, &mTraceOptionsRwLock);
+}
+
GLTraceContext *GLTraceState::createTraceContext(int version, EGLContext eglContext) {
int id = __sync_fetch_and_add(&mTraceContextIds, 1);
const size_t DEFAULT_BUFFER_SIZE = 8192;
BufferedOutputStream *stream = new BufferedOutputStream(mStream, DEFAULT_BUFFER_SIZE);
- GLTraceContext *traceContext = new GLTraceContext(id, stream);
+ GLTraceContext *traceContext = new GLTraceContext(id, this, stream);
mPerContextState[eglContext] = traceContext;
return traceContext;
@@ -87,8 +129,9 @@ GLTraceContext *GLTraceState::getTraceContext(EGLContext c) {
return mPerContextState[c];
}
-GLTraceContext::GLTraceContext(int id, BufferedOutputStream *stream) {
+GLTraceContext::GLTraceContext(int id, GLTraceState *state, BufferedOutputStream *stream) {
mId = id;
+ mState = state;
fbcontents = fbcompressed = NULL;
fbcontentsSize = 0;
@@ -99,6 +142,10 @@ int GLTraceContext::getId() {
return mId;
}
+GLTraceState *GLTraceContext::getGlobalTraceState() {
+ return mState;
+}
+
void GLTraceContext::resizeFBMemory(unsigned minSize) {
if (fbcontentsSize >= minSize) {
return;
diff --git a/opengl/libs/GLES_trace/src/gltrace_context.h b/opengl/libs/GLES_trace/src/gltrace_context.h
index 0680a9b..129116a 100644
--- a/opengl/libs/GLES_trace/src/gltrace_context.h
+++ b/opengl/libs/GLES_trace/src/gltrace_context.h
@@ -18,6 +18,7 @@
#define __GLTRACE_CONTEXT_H_
#include <map>
+#include <pthread.h>
#include "hooks.h"
#include "gltrace_transport.h"
@@ -29,9 +30,12 @@ using ::android::gl_hooks_t;
enum FBBinding {CURRENTLY_BOUND_FB, FB0};
+class GLTraceState;
+
/** GL Trace Context info associated with each EGLContext */
class GLTraceContext {
int mId; /* unique context id */
+ GLTraceState *mState; /* parent GL Trace state (for per process GL Trace State Info) */
void *fbcontents; /* memory area to read framebuffer contents */
void *fbcompressed; /* destination for lzf compressed framebuffer */
@@ -43,8 +47,9 @@ class GLTraceContext {
public:
gl_hooks_t *hooks;
- GLTraceContext(int id, BufferedOutputStream *stream);
+ GLTraceContext(int id, GLTraceState *state, BufferedOutputStream *stream);
int getId();
+ GLTraceState *getGlobalTraceState();
void getCompressedFB(void **fb, unsigned *fbsize,
unsigned *fbwidth, unsigned *fbheight,
FBBinding fbToRead);
@@ -56,6 +61,17 @@ class GLTraceState {
int mTraceContextIds;
TCPStream *mStream;
std::map<EGLContext, GLTraceContext*> mPerContextState;
+
+ /* Options controlling additional data to be collected on
+ certain trace calls. */
+ bool mCollectFbOnEglSwap;
+ bool mCollectFbOnGlDraw;
+ bool mCollectTextureDataOnGlTexImage;
+ pthread_rwlock_t mTraceOptionsRwLock;
+
+ /* helper methods to get/set values using provided lock for mutual exclusion. */
+ void safeSetValue(bool *ptr, bool value, pthread_rwlock_t *lock);
+ bool safeGetValue(bool *ptr, pthread_rwlock_t *lock);
public:
GLTraceState(TCPStream *stream);
~GLTraceState();
@@ -64,6 +80,16 @@ public:
GLTraceContext *getTraceContext(EGLContext c);
TCPStream *getStream();
+
+ /* Methods to set trace options. */
+ void setCollectFbOnEglSwap(bool en);
+ void setCollectFbOnGlDraw(bool en);
+ void setCollectTextureDataOnGlTexImage(bool en);
+
+ /* Methods to retrieve trace options. */
+ bool shouldCollectFbOnEglSwap();
+ bool shouldCollectFbOnGlDraw();
+ bool shouldCollectTextureDataOnGlTexImage();
};
void setupTraceContextThreadSpecific(GLTraceContext *context);
diff --git a/opengl/libs/GLES_trace/src/gltrace_egl.cpp b/opengl/libs/GLES_trace/src/gltrace_egl.cpp
index 50743ff..9d1682a 100644
--- a/opengl/libs/GLES_trace/src/gltrace_egl.cpp
+++ b/opengl/libs/GLES_trace/src/gltrace_egl.cpp
@@ -78,8 +78,10 @@ void GLTrace_eglSwapBuffers(void *dpy, void *draw) {
glmessage.set_context_id(glContext->getId());
glmessage.set_function(GLMessage::eglSwapBuffers);
- // read FB0 since that is what is displayed on the screen
- fixup_addFBContents(glContext, &glmessage, FB0);
+ if (glContext->getGlobalTraceState()->shouldCollectFbOnEglSwap()) {
+ // read FB0 since that is what is displayed on the screen
+ fixup_addFBContents(glContext, &glmessage, FB0);
+ }
// set start time and duration
glmessage.set_start_time(systemTime());
diff --git a/opengl/libs/GLES_trace/src/gltrace_eglapi.cpp b/opengl/libs/GLES_trace/src/gltrace_eglapi.cpp
index e04e6d4..0fe97ce 100644
--- a/opengl/libs/GLES_trace/src/gltrace_eglapi.cpp
+++ b/opengl/libs/GLES_trace/src/gltrace_eglapi.cpp
@@ -14,6 +14,7 @@
* limitations under the License.
*/
+#include <arpa/inet.h>
#include <stdlib.h>
#include <cutils/log.h>
#include <cutils/properties.h>
@@ -33,6 +34,47 @@ using gltrace::GLTraceContext;
using gltrace::TCPStream;
static GLTraceState *sGLTraceState;
+static pthread_t sReceiveThreadId;
+
+/**
+ * Task that monitors the control stream from the host and updates
+ * the trace status according to commands received from the host.
+ */
+static void *commandReceiveTask(void *arg) {
+ GLTraceState *state = (GLTraceState *)arg;
+ TCPStream *stream = state->getStream();
+
+ // Currently, there are very few user configurable settings.
+ // As a result, they can be encoded in a single integer.
+ int cmd;
+ enum TraceSettingsMasks {
+ READ_FB_ON_EGLSWAP_MASK = 1 << 0,
+ READ_FB_ON_GLDRAW_MASK = 1 << 1,
+ READ_TEXTURE_DATA_ON_GLTEXIMAGE_MASK = 1 << 2,
+ };
+
+ while (true) {
+ int n = stream->receive(&cmd, 4);
+ if (n != 4) {
+ break;
+ }
+
+ cmd = ntohl(cmd);
+
+ bool collectFbOnEglSwap = (cmd & READ_FB_ON_EGLSWAP_MASK) != 0;
+ bool collectFbOnGlDraw = (cmd & READ_FB_ON_GLDRAW_MASK) != 0;
+ bool collectTextureData = (cmd & READ_TEXTURE_DATA_ON_GLTEXIMAGE_MASK) != 0;
+
+ state->setCollectFbOnEglSwap(collectFbOnEglSwap);
+ state->setCollectFbOnGlDraw(collectFbOnGlDraw);
+ state->setCollectTextureDataOnGlTexImage(collectTextureData);
+
+ ALOGD("trace options: eglswap: %d, gldraw: %d, texImage: %d",
+ collectFbOnEglSwap, collectFbOnGlDraw, collectTextureData);
+ }
+
+ return NULL;
+}
void GLTrace_start() {
char value[PROPERTY_VALUE_MAX];
@@ -51,6 +93,8 @@ void GLTrace_start() {
// initialize tracing state
sGLTraceState = new GLTraceState(stream);
+
+ pthread_create(&sReceiveThreadId, NULL, commandReceiveTask, sGLTraceState);
}
void GLTrace_stop() {
diff --git a/opengl/libs/GLES_trace/src/gltrace_fixup.cpp b/opengl/libs/GLES_trace/src/gltrace_fixup.cpp
index 7fbae1de..5a439e3 100644
--- a/opengl/libs/GLES_trace/src/gltrace_fixup.cpp
+++ b/opengl/libs/GLES_trace/src/gltrace_fixup.cpp
@@ -283,7 +283,9 @@ void fixupGLMessage(GLTraceContext *context, nsecs_t start, nsecs_t end, GLMessa
fixup_glGetString(glmsg);
break;
case GLMessage::glTexImage2D:
- fixup_glTexImage2D(glmsg);
+ if (context->getGlobalTraceState()->shouldCollectTextureDataOnGlTexImage()) {
+ fixup_glTexImage2D(glmsg);
+ }
break;
case GLMessage::glShaderSource:
fixup_glShaderSource(glmsg);
@@ -304,10 +306,16 @@ void fixupGLMessage(GLTraceContext *context, nsecs_t start, nsecs_t end, GLMessa
fixup_glUniformMatrixGeneric(4, glmsg);
break;
case GLMessage::glDrawArrays:
- case GLMessage::glDrawElements:
/* void glDrawArrays(GLenum mode, GLint first, GLsizei count) */
+ if (context->getGlobalTraceState()->shouldCollectFbOnGlDraw()) {
+ fixup_addFBContents(context, glmsg, CURRENTLY_BOUND_FB);
+ }
+ break;
+ case GLMessage::glDrawElements:
/* void glDrawElements(GLenum mode, GLsizei count, GLenum type, const GLvoid* indices) */
- fixup_addFBContents(context, glmsg, CURRENTLY_BOUND_FB);
+ if (context->getGlobalTraceState()->shouldCollectFbOnGlDraw()) {
+ fixup_addFBContents(context, glmsg, CURRENTLY_BOUND_FB);
+ }
break;
default:
break;