[Libva] [PATCH V2][libva] add the support of multiple context tracing

Chen, Peng C peng.c.chen at intel.com
Wed May 11 06:00:23 UTC 2016


Yes, you are right. this patch fixes the problem of the first case.

-----Original Message-----
From: Yuan, Shengquan 
Sent: Wednesday, May 11, 2016 1:55 PM
To: Chen, Peng C <peng.c.chen at intel.com>; libva at lists.freedesktop.org
Subject: RE: [Libva] [PATCH V2][libva] add the support of multiple context tracing

You mean multiple vaCreateContext in one parried vaGetDisplay/vaInit/vaTerminate? Like the sequence below:
	vaGetDisplay
	vaInitialize
	vaCreateContext #create context 1
	.....
	vaCreateContext #create context 2
	......
	vaTerminate
Such sequence will have issue in VA trace.  Context 2 and 1 log will mix up

If each vaCreateContext has its own vaGetDisplay/vaInit/vaTermintae, VA trace should work: each context has its own log
	vaGetDisplay
	vaInitialize
	vaCreateContext #create context 1
	.....
	vaTerminate

	vaGetDisplay
	vaInitialize
	vaCreateContext #create context 2
	.......
	vaTerminate

-----Original Message-----
From: Chen, Peng C 
Sent: Wednesday, May 11, 2016 1:43 PM
To: Yuan, Shengquan <shengquan.yuan at intel.com>; libva at lists.freedesktop.org
Subject: RE: [Libva] [PATCH V2][libva] add the support of multiple context tracing

Hi yuan,shengquan,
	Libva has a limited tracing function before. if more than one context is created
in one process, then this tracing can't work and output wrong log messages. 
	This patch fixes this problem. Tracing is possible while multiple contexts are being
used.
	And I think, it is especially usefully for debugging multiple windows player or other using
a lot of contexts application.

-----Original Message-----
From: Yuan, Shengquan 
Sent: Wednesday, May 11, 2016 10:43 AM
To: Chen, Peng C <peng.c.chen at intel.com>; libva at lists.freedesktop.org
Subject: RE: [Libva] [PATCH V2][libva] add the support of multiple context tracing

Peng, 

Could you provide more details about this change? Which problem are your trying to solve?

Thanks
-Austin

-----Original Message-----
From: Libva [mailto:libva-bounces at lists.freedesktop.org] On Behalf Of peng.chen
Sent: Wednesday, May 11, 2016 10:38 AM
To: libva at lists.freedesktop.org
Subject: [Libva] [PATCH V2][libva] add the support of multiple context tracing

Signed-off-by: peng.chen <peng.c.chen at intel.com>
---
 va/va.c       |   16 +-
 va/va_trace.c | 1260 +++++++++++++++++++++++++++++++++++++++++++++++----------
 va/va_trace.h |   12 +
 3 files changed, 1069 insertions(+), 219 deletions(-)

diff --git a/va/va.c b/va/va.c
index 9bdb041..cd88d67 100644
--- a/va/va.c
+++ b/va/va.c
@@ -740,10 +740,16 @@ VAStatus vaDestroyConfig (
 )
 {
   VADriverContextP ctx;
+  VAStatus vaStatus = VA_STATUS_SUCCESS;
+
   CHECK_DISPLAY(dpy);
   ctx = CTX(dpy);
 
-  return ctx->vtable->vaDestroyConfig ( ctx, config_id );
+  vaStatus = ctx->vtable->vaDestroyConfig ( ctx, config_id );
+
+  VA_TRACE_ALL(va_TraceDestroyConfig, dpy, config_id);
+
+  return vaStatus;
 }
 
 VAStatus vaQueryConfigAttributes (
@@ -1015,10 +1021,16 @@ VAStatus vaDestroyContext (
 )
 {
   VADriverContextP ctx;
+  VAStatus vaStatus;
+
   CHECK_DISPLAY(dpy);
   ctx = CTX(dpy);
 
-  return ctx->vtable->vaDestroyContext( ctx, context );
+  vaStatus = ctx->vtable->vaDestroyContext( ctx, context );
+
+  VA_TRACE_ALL(va_TraceDestroyContext, dpy, context);
+
+  return vaStatus;
 }
 
 VAStatus vaCreateBuffer (
diff --git a/va/va_trace.c b/va/va_trace.c
index 0e6cded..f632176 100644
--- a/va/va_trace.c
+++ b/va/va_trace.c
@@ -46,6 +46,8 @@
 #include <unistd.h>
 #include <sys/types.h>
 #include <sys/stat.h>
+#include <sys/syscall.h>
+#include <pthread.h>
 #include <unistd.h>
 #include <time.h>
 #include <errno.h>
@@ -66,16 +68,49 @@
 /* LIBVA_TRACE */
 int trace_flag = 0;
 
+#define MAX_TRACE_CTX_NUM   64
+#define TRACE_CTX_ID_MASK      (MAX_TRACE_CTX_NUM - 1)
+
+#define MAX_TRACE_THREAD_NUM   64
+
+#define MAX_TRACE_BUF_INFO_HASH_SIZE     1024 // 1<<10
+#define MAX_TRACE_BUF_INFO_HASH_LEVEL    3
+#define TRACE_BUF_INFO_HASH_ID_MASK         (MAX_TRACE_BUF_INFO_HASH_SIZE - 1)
+
+struct trace_buf_info {
+    int valid;
+
+    VABufferID buf_id;
+    VAContextID ctx_id;
+};
+
+struct trace_buf_manager {
+    struct trace_buf_info *pbuf_info[MAX_TRACE_BUF_INFO_HASH_LEVEL];
+};
+
+struct trace_log_file {
+    pid_t thread_id;
+    int used;
+
+    char *fn_log;
+    FILE *fp_log;
+};
+
+struct trace_log_files_manager {
+    int num;
+
+    struct trace_log_file log_file[MAX_TRACE_THREAD_NUM];
+};
+
 /* per context settings */
 struct trace_context {
-    /* LIBVA_TRACE */
-    FILE *trace_fp_log; /* save the log into a file */
-    char *trace_log_fn; /* file name */
-    
+    struct trace_log_file *plog_file;
+    struct trace_log_file *plog_file_list[MAX_TRACE_THREAD_NUM];
+
     /* LIBVA_TRACE_CODEDBUF */
     FILE *trace_fp_codedbuf; /* save the encode result into a file */
     char *trace_codedbuf_fn; /* file name */
-    
+
     /* LIBVA_TRACE_SURFACE */
     FILE *trace_fp_surface; /* save the surface YUV into a file */
     char *trace_surface_fn; /* file name */
@@ -99,15 +134,97 @@ struct trace_context {
     unsigned int trace_frame_height; /* current frame height */
 
     unsigned int pts; /* IVF header information */
+
+    pid_t created_thd_id;
 };
 
-#define TRACE_CTX(dpy) ((struct trace_context *)((VADisplayContextP)dpy)->vatrace)
+struct trace_config_info {
+    int valid;
+    VAConfigID config_id;
 
-#define DPY2TRACECTX(dpy)                               \
-    struct trace_context *trace_ctx = TRACE_CTX(dpy);   \
-                                                        \
-    if (trace_ctx == NULL)                              \
-        return;                                         \
+    VAProfile trace_profile;
+    VAEntrypoint trace_entrypoint;
+
+    pid_t created_thd_id;
+};
+
+struct va_trace {
+    struct trace_context *ptra_ctx[MAX_TRACE_CTX_NUM + 1];
+    int context_num;
+    struct trace_buf_manager buf_manager;
+    struct trace_log_files_manager log_files_manager;
+    struct trace_config_info config_info[MAX_TRACE_CTX_NUM];
+
+    char *fn_log_env;
+    char *fn_codedbuf_env;
+    char *fn_surface_env;
+
+    pthread_mutex_t resource_mutex;
+    pthread_mutex_t context_mutex;
+};
+
+#define LOCK_RESOURCE(pva_trace)                                    \
+    if(pva_trace)                                                   \
+        pthread_mutex_lock(&pva_trace->resource_mutex)
+
+#define UNLOCK_RESOURCE(pva_trace)                                  \
+    if(pva_trace)                                                   \
+        pthread_mutex_unlock(&pva_trace->resource_mutex)
+
+#define LOCK_CONTEXT(pva_trace)                                     \
+        if(pva_trace)                                               \
+            pthread_mutex_lock(&pva_trace->context_mutex)
+
+#define UNLOCK_CONTEXT(pva_trace)                                   \
+        if(pva_trace)                                               \
+            pthread_mutex_unlock(&pva_trace->context_mutex)
+
+#define DPY2TRACECTX(dpy, context, buf_id)                                  \
+    struct va_trace *pva_trace = NULL;                                      \
+    struct trace_context *trace_ctx = NULL;                                 \
+    int ctx_id = context;                                                   \
+                                                                            \
+    pva_trace = (struct va_trace *)(((VADisplayContextP)dpy)->vatrace);     \
+    if(!pva_trace)                                                          \
+        return;                                                             \
+                                                                            \
+    if(ctx_id == VA_INVALID_ID) {                                           \
+        if(buf_id != VA_INVALID_ID)                                         \
+            ctx_id = get_ctx_by_buf(pva_trace, buf_id);                     \
+        else                                                                \
+            return;                                                         \
+    }                                                                       \
+                                                                            \
+    if (ctx_id != VA_INVALID_ID) {                                          \
+        int temp_idx = get_valid_ctx_idx(pva_trace, ctx_id);                \
+        if(temp_idx < MAX_TRACE_CTX_NUM)                                    \
+            trace_ctx = pva_trace->ptra_ctx[temp_idx];                      \
+    }                                                                       \
+                                                                            \
+    if(!trace_ctx                                                           \
+        || trace_ctx->trace_context != context) {                           \
+        return;                                                             \
+    }                                                                       \
+    refresh_log_file(pva_trace, trace_ctx)
+
+#define DPY2TRACE_VIRCTX(dpy)                                               \
+    struct va_trace *pva_trace = NULL;                                      \
+    struct trace_context *trace_ctx = NULL;                                 \
+                                                                            \
+    pva_trace = (struct va_trace *)(((VADisplayContextP)dpy)->vatrace);     \
+    if(!pva_trace)                                                          \
+        return;                                                             \
+                                                                            \
+    LOCK_CONTEXT(pva_trace);                                                \
+    trace_ctx = pva_trace->ptra_ctx[MAX_TRACE_CTX_NUM];                     \
+    if(!trace_ctx) {                                                        \
+        UNLOCK_CONTEXT(pva_trace);                                          \
+        return;                                                             \
+    }                                                                       \
+    refresh_log_file(pva_trace, trace_ctx)
+
+#define DPY2TRACE_VIRCTX_EXIT(pva_trace)                                \
+    UNLOCK_CONTEXT(pva_trace)
 
 #define TRACE_FUNCNAME(idx)    va_TraceMsg(trace_ctx, "==========%s\n", __func__); 
 
@@ -144,63 +261,507 @@ VAStatus vaUnlockSurface(VADisplay dpy,
                          VASurfaceID surface
                          );
 
-#define FILE_NAME_SUFFIX(env_value)                      \
-do {                                                    \
-    int tmp = strnlen(env_value, sizeof(env_value));    \
-    int left = sizeof(env_value) - tmp;                 \
-                                                        \
-    snprintf(env_value+tmp,                             \
-             left,                                      \
-             ".%04d.%08lx",                             \
-             suffix,                                    \
-             (unsigned long)trace_ctx);                 \
-} while (0)
+static int get_valid_config_idx(
+    struct va_trace *pva_trace,
+    VAConfigID config_id)
+{
+    struct trace_config_info *pconfig_info;
+    int idx = MAX_TRACE_CTX_NUM;
+
+    LOCK_RESOURCE(pva_trace);
+
+    pconfig_info = pva_trace->config_info;
+    idx = config_id & TRACE_CTX_ID_MASK;
+    if(!pconfig_info[idx].valid
+        || pconfig_info[idx].config_id != config_id)
+        idx = MAX_TRACE_CTX_NUM;
+
+    UNLOCK_RESOURCE(pva_trace);
+
+    return idx;
+}
+
+static void add_trace_config_info(
+    struct va_trace *pva_trace,
+    VAConfigID config_id,
+    VAProfile profile,
+    VAEntrypoint entrypoint)
+{
+    struct trace_config_info *pconfig_info;
+    int idx = 0;
+    pid_t thd_id = syscall(__NR_gettid);
+
+    LOCK_RESOURCE(pva_trace);
+
+    idx = config_id & TRACE_CTX_ID_MASK;
+    pconfig_info = &pva_trace->config_info[idx];
+    if(!pconfig_info->valid ||
+        pconfig_info->config_id == config_id) {
+        pconfig_info->valid = 1;
+        pconfig_info->config_id = config_id;
+        pconfig_info->trace_profile = profile;
+        pconfig_info->trace_entrypoint = entrypoint;
+        pconfig_info->created_thd_id = thd_id;
+    }
+
+    UNLOCK_RESOURCE(pva_trace);
+}
+
+static void delete_trace_config_info(
+    struct va_trace *pva_trace,
+    VAConfigID config_id)
+{
+    struct trace_config_info *pconfig_info;
+    int idx = 0;
+    pid_t thd_id = syscall(__NR_gettid);
+
+    LOCK_RESOURCE(pva_trace);
+
+    idx = config_id & TRACE_CTX_ID_MASK;
+    pconfig_info = &pva_trace->config_info[idx];
+    if(pconfig_info->valid &&
+		pconfig_info->config_id == config_id &&
+		pconfig_info->created_thd_id == thd_id) {
+        pconfig_info->valid = 0;
+    }
+
+    UNLOCK_RESOURCE(pva_trace);
+}
+
+static VAContextID get_ctx_by_buf(
+    struct va_trace *pva_trace,
+    VABufferID buf_id)
+{
+    struct trace_buf_manager *pbuf_mgr = &pva_trace->buf_manager;
+    struct trace_buf_info *pbuf_info = pbuf_mgr->pbuf_info[0];
+    VAContextID context = VA_INVALID_ID;
+    int i = 0, idx = 0, valid = 0;
+
+    LOCK_RESOURCE(pva_trace);
+
+    idx = buf_id & TRACE_BUF_INFO_HASH_ID_MASK;
+    for(i = 0;i < MAX_TRACE_BUF_INFO_HASH_LEVEL;i++) {
+        pbuf_info = pbuf_mgr->pbuf_info[i];
+        if(!pbuf_info)
+            break;
+
+        if(pbuf_info[idx].valid
+            && pbuf_info[idx].buf_id == buf_id) {
+            context = pbuf_info[idx].ctx_id;
+            break;
+        }
+    }
+
+    UNLOCK_RESOURCE(pva_trace);
+
+    return context;
+}
+
+static void add_trace_buf_info(
+    struct va_trace *pva_trace,
+    VAContextID context,
+    VABufferID buf_id)
+{
+    struct trace_buf_manager *pbuf_mgr = &pva_trace->buf_manager;
+    struct trace_buf_info *pbuf_info = NULL;
+    int i = 0, idx = 0;
+
+    LOCK_RESOURCE(pva_trace);
+
+    idx = buf_id & TRACE_BUF_INFO_HASH_ID_MASK;
+    for(i = 0;i < MAX_TRACE_BUF_INFO_HASH_LEVEL;i++) {
+        pbuf_info = pbuf_mgr->pbuf_info[i];
+        if(!pbuf_info) {
+            pbuf_info = (struct trace_buf_info *)calloc(
+                sizeof(struct trace_buf_info) * MAX_TRACE_BUF_INFO_HASH_SIZE,
+                1);
+            if(!pbuf_info)
+                break;
+
+            pbuf_mgr->pbuf_info[i] = pbuf_info;
+        }
+
+        if(pbuf_info[idx].valid
+            && pbuf_info[idx].buf_id != buf_id)
+            continue;
+
+        pbuf_info[idx].buf_id = buf_id;
+        pbuf_info[idx].ctx_id = context;
+        pbuf_info[idx].valid = 1;
+        break;
+    }
+
+    if(i >= MAX_TRACE_BUF_INFO_HASH_LEVEL)
+        va_errorMessage("Add buf info failed\n");
+
+    UNLOCK_RESOURCE(pva_trace);
+}
+
+static void delete_trace_buf_info(
+    struct va_trace *pva_trace,
+    VABufferID buf_id)
+{
+    struct trace_buf_manager *pbuf_mgr = &pva_trace->buf_manager;
+    struct trace_buf_info *pbuf_info = NULL;
+    int i = 0, idx = 0;
+
+    LOCK_RESOURCE(pva_trace);
+
+    idx = buf_id & TRACE_BUF_INFO_HASH_ID_MASK;
+    for(i = 0;i < MAX_TRACE_BUF_INFO_HASH_LEVEL;i++) {
+        pbuf_info = pbuf_mgr->pbuf_info[i];
+        if(!pbuf_info)
+            break;
+
+        if(pbuf_info[idx].valid
+            && pbuf_info[idx].buf_id == buf_id) {
+            pbuf_info[idx].valid = 0;
+            break;
+        }
+    }
+
+    UNLOCK_RESOURCE(pva_trace);
+}
+
+/*
+static void delete_trace_all_context_buf(
+    struct va_trace *pva_trace,
+    VAContextID context)
+{
+    struct trace_buf_manager *pbuf_mgr = &pva_trace->buf_manager;
+    struct trace_buf_info *pbuf_info = NULL;
+    int i = 0, j = 0;
+
+    LOCK_RESOURCE(pva_trace);
+
+    for(i = 0;i < MAX_TRACE_BUF_INFO_HASH_LEVEL;i++) {
+        pbuf_info = pbuf_mgr->pbuf_info[i];
+        if(!pbuf_info)
+            break;
+
+        for(j = 0;j < MAX_TRACE_BUF_INFO_HASH_SIZE;j++)
+            if(pbuf_info[j].valid
+                && pbuf_info[j].ctx_id == context)
+                pbuf_info[j].valid = 0;
+    }
+
+    UNLOCK_RESOURCE(pva_trace);
+}
+*/
+
+static int get_free_ctx_idx(
+    struct va_trace *pva_trace,
+    VAContextID context)
+{
+    int idx = MAX_TRACE_CTX_NUM;
+    int i = 0;
+
+    LOCK_RESOURCE(pva_trace);
+
+    i = context & TRACE_CTX_ID_MASK;
+    if(!pva_trace->ptra_ctx[i]
+        || pva_trace->ptra_ctx[i]->trace_context == context)
+        idx = i;
+
+    UNLOCK_RESOURCE(pva_trace);
+
+    return idx;
+}
+
+static int get_valid_ctx_idx(
+    struct va_trace *pva_trace,
+    VAContextID context)
+{
+    int idx = MAX_TRACE_CTX_NUM;
+    int i = 0;
+
+    LOCK_RESOURCE(pva_trace);
+
+    i = context & TRACE_CTX_ID_MASK;
+    if(pva_trace->ptra_ctx[i]
+        && pva_trace->ptra_ctx[i]->trace_context == context)
+        idx = i;
+
+    UNLOCK_RESOURCE(pva_trace);
+
+    return idx;
+}
+
+static void FILE_NAME_SUFFIX(
+    char *env_value,
+    int max_size,
+    char *suffix_str,
+    unsigned int suffix_handle)
+{
+    int tmp = strnlen(env_value, max_size);
+    int left = max_size - tmp;
+    struct timeval tv;
+    int size = strlen(suffix_str);
+
+    if(left < (size + 8 + 10))
+        return;
+
+    if(gettimeofday(&tv, NULL) == 0) {
+        sprintf(env_value + tmp,
+            ".%02d%02d%02d.",
+            (unsigned int)(tv.tv_sec/3600)%24,
+            (unsigned int)(tv.tv_sec/60)%60,
+            (unsigned int)tv.tv_sec%60);
+
+        tmp += 8;
+        left -= 8;
+    }
+
+    if(suffix_str) {
+        strcat(env_value + tmp,
+            suffix_str);
+
+        tmp += size;
+        left -= size;
+    }
+
+    if(suffix_handle) {
+        sprintf(env_value + tmp,
+            "0x%08x",
+            suffix_handle);
+    }
+}
+
+static int open_tracing_specil_file(
+    struct va_trace *pva_trace,
+    struct trace_context *ptra_ctx,
+    int type) // 0: codedbuf, 1: surface
+{
+    char *fn_env = type == 0 ?
+        pva_trace->fn_codedbuf_env : pva_trace->fn_surface_env;
+    char env_value[1024];
+    FILE *fp = NULL;
+
+    strncpy(env_value, fn_env, 1024);
+    FILE_NAME_SUFFIX(env_value, 1024,
+        "ctx-", (unsigned int)ptra_ctx->trace_context);
+
+    fn_env = strdup(env_value);
+    if(!fn_env)
+        return -1;
+
+    fp = fopen(fn_env, "w");
+    if(!fp) {
+        free(fn_env);
+
+        return -1;
+    }
+
+    if(type == 0) {
+        ptra_ctx->trace_codedbuf_fn = fn_env;
+        ptra_ctx->trace_fp_codedbuf = fp;
+        va_infoMessage("LIBVA_TRACE_CODEDBUF is on, save codedbuf into %s\n",
+            fn_env);
+    }
+    else {
+        ptra_ctx->trace_surface_fn = fn_env;
+        ptra_ctx->trace_fp_surface = fp;
+        va_infoMessage("LIBVA_TRACE_SURFACE is on, save surface into %s\n",
+            fn_env);
+    }
+
+    return 0;
+}
+
+static int open_tracing_log_file(
+    struct va_trace *pva_trace,
+    struct trace_log_file *plog_file,
+    pid_t thd_id)
+{
+    FILE *pfp = NULL;
+    int new_fn_flag = 0;
+
+    if(plog_file->used && plog_file->thread_id != thd_id) {
+        va_errorMessage("Try to open a busy log file occupied by other thread\n");
+
+        return -1;
+    }
+
+    if(plog_file->thread_id != thd_id) {
+        char env_value[1024];
+
+        strncpy(env_value, pva_trace->fn_log_env, 1024);
+        FILE_NAME_SUFFIX(env_value, 1024,
+            "thd-", (unsigned int)thd_id);
+
+        if(plog_file->fn_log)
+            free(plog_file->fn_log);
+
+        plog_file->fn_log = strdup(env_value);
+        if(!plog_file->fn_log)
+            goto FAIL;
+
+        new_fn_flag = 1;
+    }
+
+    if(!plog_file->used) {
+        if(new_fn_flag)
+            pfp = fopen(plog_file->fn_log, "w");
+        else
+            pfp = fopen(plog_file->fn_log, "a");
+
+        if(!pfp)
+            goto FAIL;
+
+        va_infoMessage("%s %s for the thread 0x%08x\n",
+            new_fn_flag ? "Open new log file" : "Append to log file",
+            plog_file->fn_log, thd_id);
+
+        plog_file->fp_log = pfp;
+        plog_file->thread_id = thd_id;
+    }
+
+    plog_file->used++;
+    return 0;
+
+FAIL:
+    if(plog_file->fn_log) {
+        free(plog_file->fn_log);
+        plog_file->fn_log = NULL;
+    }
+
+    return -1;
+}
+
+static int get_log_file_idx_by_thd(
+    struct trace_log_files_manager *plog_files_mgr,
+    pid_t thd_id)
+{
+    struct trace_log_file *plog_file = plog_files_mgr->log_file;
+    int first_free_idx = MAX_TRACE_THREAD_NUM;
+    int i = 0;
+
+    for(i = 0;i < MAX_TRACE_THREAD_NUM;i++) {
+        if(plog_file[i].thread_id == thd_id)
+            break;
+        else if(!plog_file[i].used &&
+            first_free_idx >= MAX_TRACE_THREAD_NUM)
+            first_free_idx = i;
+    }
+
+    if(i >= MAX_TRACE_THREAD_NUM)
+        i = first_free_idx;
+
+    return i;
+}
+
+static struct trace_log_file *start_tracing2log_file(
+    struct va_trace *pva_trace)
+{
+    struct trace_log_files_manager *plog_files_mgr = NULL;
+    struct trace_log_file *plog_file = NULL;
+    pid_t thd_id = syscall(__NR_gettid);
+    int i = 0;
+
+    LOCK_RESOURCE(pva_trace);
+
+    plog_files_mgr = &pva_trace->log_files_manager;
+    i = get_log_file_idx_by_thd(plog_files_mgr, thd_id);
+    if(i < MAX_TRACE_THREAD_NUM) {
+        plog_file = &plog_files_mgr->log_file[i];
+        if(open_tracing_log_file(pva_trace, plog_file, thd_id) < 0) {
+            plog_file = NULL;
+        }
+    }
+
+    UNLOCK_RESOURCE(pva_trace);
+    return plog_file;
+}
+
+static void stop_tracing2log_file(
+    struct va_trace *pva_trace,
+    struct trace_log_file *plog_file)
+{
+    LOCK_RESOURCE(pva_trace);
+
+    if(--plog_file->used <= 0) {
+        if(plog_file->fp_log) {
+            fclose(plog_file->fp_log);
+            plog_file->fp_log = NULL;
+        }
+    }
+
+    UNLOCK_RESOURCE(pva_trace);
+}
+
+static void refresh_log_file(
+    struct va_trace *pva_trace,
+    struct trace_context *ptra_ctx)
+{
+    struct trace_log_file *plog_file = NULL;
+    pid_t thd_id = syscall(__NR_gettid);
+    int i = 0;
+
+    plog_file = ptra_ctx->plog_file;
+    if(plog_file && plog_file->thread_id != thd_id) {
+        plog_file = start_tracing2log_file(pva_trace);
+        if(plog_file) {
+            int first_free_idx = -1;
+
+            ptra_ctx->plog_file = plog_file;
+
+            for(i = 0;i < MAX_TRACE_THREAD_NUM;i++) {
+                if(!ptra_ctx->plog_file_list[i]){
+                    if(first_free_idx < 0)
+                        first_free_idx = i;
+                }
+                else if(ptra_ctx->plog_file_list[i]->thread_id == thd_id)
+                    break;
+            }
+
+            if(i > MAX_TRACE_THREAD_NUM
+                && first_free_idx >= 0)
+                ptra_ctx->plog_file_list[first_free_idx] = plog_file;
+        }
+    }
+}
 
 void va_TraceInit(VADisplay dpy)
 {
     char env_value[1024];
     unsigned short suffix = 0xffff & ((unsigned int)time(NULL));
     int trace_index = 0;
-    FILE *tmp;    
+    FILE *tmp;
+    struct va_trace *pva_trace = calloc(sizeof(struct va_trace), 1);
     struct trace_context *trace_ctx = calloc(sizeof(struct trace_context), 1);
 
-    if (trace_ctx == NULL)
+    if (pva_trace == NULL || trace_ctx == NULL)
         return;
-    
+
     if (va_parseConfig("LIBVA_TRACE", &env_value[0]) == 0) {
-        FILE_NAME_SUFFIX(env_value);
-        trace_ctx->trace_log_fn = strdup(env_value);
-        
-        tmp = fopen(env_value, "w");
-        if (tmp) {
-            trace_ctx->trace_fp_log = tmp;
-            va_infoMessage("LIBVA_TRACE is on, save log into %s\n", trace_ctx->trace_log_fn);
+        pva_trace->fn_log_env = strdup(env_value);
+        trace_ctx->plog_file = start_tracing2log_file(pva_trace);
+        if(trace_ctx->plog_file) {
+            trace_ctx->plog_file_list[0] = trace_ctx->plog_file;
             trace_flag = VA_TRACE_FLAG_LOG;
-        } else
+
+            va_infoMessage("LIBVA_TRACE is on, save log into %s\n",
+                trace_ctx->plog_file->fn_log);
+        }
+        else
             va_errorMessage("Open file %s failed (%s)\n", env_value, strerror(errno));
     }
 
     /* may re-get the global settings for multiple context */
     if ((trace_flag & VA_TRACE_FLAG_LOG) && (va_parseConfig("LIBVA_TRACE_BUFDATA", NULL) == 0)) {
         trace_flag |= VA_TRACE_FLAG_BUFDATA;
+
         va_infoMessage("LIBVA_TRACE_BUFDATA is on, dump buffer into log file\n");
     }
 
     /* per-context setting */
     if (va_parseConfig("LIBVA_TRACE_CODEDBUF", &env_value[0]) == 0) {
-        FILE_NAME_SUFFIX(env_value);
-        trace_ctx->trace_codedbuf_fn = strdup(env_value);
-        va_infoMessage("LIBVA_TRACE_CODEDBUF is on, save codedbuf into log file %s\n",
-                       trace_ctx->trace_codedbuf_fn);
+        pva_trace->fn_codedbuf_env = strdup(env_value);
         trace_flag |= VA_TRACE_FLAG_CODEDBUF;
     }
 
     if (va_parseConfig("LIBVA_TRACE_SURFACE", &env_value[0]) == 0) {
-        FILE_NAME_SUFFIX(env_value);
-        trace_ctx->trace_surface_fn = strdup(env_value);
-
-        va_infoMessage("LIBVA_TRACE_SURFACE is on, save surface into %s\n",
-                       trace_ctx->trace_surface_fn);
+        pva_trace->fn_surface_env = strdup(env_value);
 
         /* for surface data dump, it is time-consume, and may
          * cause some side-effect, so only trace the needed surfaces
@@ -234,58 +795,119 @@ void va_TraceInit(VADisplay dpy)
         }
     }
 
-    ((VADisplayContextP)dpy)->vatrace = trace_ctx;
-}
+    pthread_mutex_init(&pva_trace->resource_mutex, NULL);
+    pthread_mutex_init(&pva_trace->context_mutex, NULL);
+
+    trace_ctx->trace_context = VA_INVALID_ID;
+    pva_trace->ptra_ctx[MAX_TRACE_CTX_NUM] = trace_ctx;
 
+    ((VADisplayContextP)dpy)->vatrace = (void *)pva_trace;
+
+    if(!trace_flag)
+        va_TraceEnd(dpy);
+}
 
 void va_TraceEnd(VADisplay dpy)
 {
-    DPY2TRACECTX(dpy);
-    
-    if (trace_ctx->trace_fp_log)
-        fclose(trace_ctx->trace_fp_log);
-    
-    if (trace_ctx->trace_fp_codedbuf)
-        fclose(trace_ctx->trace_fp_codedbuf);
-    
-    if (trace_ctx->trace_fp_surface)
-        fclose(trace_ctx->trace_fp_surface);
+    struct va_trace *pva_trace = NULL;
+    int i = 0, j = 0;
 
-    if (trace_ctx->trace_log_fn)
-        free(trace_ctx->trace_log_fn);
-    
-    if (trace_ctx->trace_codedbuf_fn)
-        free(trace_ctx->trace_codedbuf_fn);
-    
-    if (trace_ctx->trace_surface_fn)
-        free(trace_ctx->trace_surface_fn);
-    
-    free(trace_ctx);
+    pva_trace = (struct va_trace *)(((VADisplayContextP)dpy)->vatrace);
+    if(!pva_trace)
+        return;
+
+    if(pva_trace->fn_log_env)
+        free(pva_trace->fn_log_env);
+
+    if(pva_trace->fn_codedbuf_env)
+        free(pva_trace->fn_codedbuf_env);
+
+    if(pva_trace->fn_surface_env)
+        free(pva_trace->fn_surface_env);
+
+    for(i = 0;i < MAX_TRACE_BUF_INFO_HASH_LEVEL;i++)
+        if(pva_trace->buf_manager.pbuf_info[i])
+            free(pva_trace->buf_manager.pbuf_info[i]);
+
+    for(i = 0;i < MAX_TRACE_THREAD_NUM;i++) {
+        struct trace_log_file *plog_file = NULL;
+
+        if(pva_trace->log_files_manager.num <= 0)
+            break;
+
+        plog_file = &pva_trace->log_files_manager.log_file[i];
+        if(plog_file) {
+            if(plog_file->fn_log)
+                free(plog_file->fn_log);
+
+            if(plog_file->fp_log)
+                fclose(plog_file->fp_log);
+
+            pva_trace->log_files_manager.num--;
+        }
+    }
+
+    for(i = 0;i < MAX_TRACE_CTX_NUM;i++) {
+        struct trace_context *trace_ctx = NULL;
+
+        if(pva_trace->context_num <= 0)
+            break;
+
+        trace_ctx = pva_trace->ptra_ctx[i];
+        if(trace_ctx) {
+            if(trace_ctx->trace_codedbuf_fn)
+                free(trace_ctx->trace_codedbuf_fn);
+
+            if(trace_ctx->trace_fp_codedbuf)
+                fclose(trace_ctx->trace_fp_codedbuf);
+
+            if(trace_ctx->trace_surface_fn)
+                free(trace_ctx->trace_surface_fn);
+
+            if(trace_ctx->trace_fp_surface)
+                fclose(trace_ctx->trace_fp_surface);
+
+            free(pva_trace->ptra_ctx[i]);
+            pva_trace->context_num--;
+        }
+    }
+    free(pva_trace->ptra_ctx[MAX_TRACE_CTX_NUM]);
+
+    free(pva_trace);
     ((VADisplayContextP)dpy)->vatrace = NULL;
 }
 
 static void va_TraceMsg(struct trace_context *trace_ctx, const char *msg, ...)
 {
+    FILE *fp = NULL;
     va_list args;
 
-    if (!(trace_flag & VA_TRACE_FLAG_LOG))
+    if (!(trace_flag & VA_TRACE_FLAG_LOG)
+        || !trace_ctx->plog_file)
         return;
 
+    fp = trace_ctx->plog_file->fp_log;
     if (msg)  {
         struct timeval tv;
 
         if (gettimeofday(&tv, NULL) == 0)
-            fprintf(trace_ctx->trace_fp_log, "[%04d.%06d] ",
-                    (unsigned int)tv.tv_sec & 0xffff, (unsigned int)tv.tv_usec);
+            fprintf(fp, "[%04d.%06d]",
+                (unsigned int)tv.tv_sec & 0xffff, (unsigned int)tv.tv_usec);
+
+        if(trace_ctx->trace_context != VA_INVALID_ID)
+            fprintf(fp,
+                "[ctx 0x%08x]", trace_ctx->trace_context);
+        else
+            fprintf(fp, "[ctx       none]");
+
         va_start(args, msg);
-        vfprintf(trace_ctx->trace_fp_log, msg, args);
+        vfprintf(fp, msg, args);
         va_end(args);
     } else
-        fflush(trace_ctx->trace_fp_log);
+        fflush(fp);
 }
 
-
-static void va_TraceSurface(VADisplay dpy)
+static void va_TraceSurface(VADisplay dpy, VAContextID context)
 {
     unsigned int i, j;
     unsigned int fourcc; /* following are output argument */
@@ -300,7 +922,7 @@ static void va_TraceSurface(VADisplay dpy)
     unsigned char *Y_data, *UV_data, *tmp;
     VAStatus va_status;
     unsigned char check_sum = 0;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     if (!trace_ctx->trace_fp_surface)
         return;
@@ -364,6 +986,8 @@ static void va_TraceSurface(VADisplay dpy)
         }
     }
 
+    fflush(trace_ctx->trace_fp_surface);
+
     vaUnlockSurface(dpy, trace_ctx->trace_rendertarget);
 
     va_TraceMsg(trace_ctx, NULL);
@@ -376,16 +1000,19 @@ void va_TraceInitialize (
     int *minor_version      /* out */
 )
 {
-    DPY2TRACECTX(dpy);    
+    DPY2TRACE_VIRCTX(dpy);
     TRACE_FUNCNAME(idx);
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
 }
 
 void va_TraceTerminate (
     VADisplay dpy
 )
 {
-    DPY2TRACECTX(dpy);    
+    DPY2TRACE_VIRCTX(dpy);
     TRACE_FUNCNAME(idx);
+    va_TraceMsg(trace_ctx, NULL);
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
 }
 
 
@@ -399,8 +1026,8 @@ void va_TraceCreateConfig(
 )
 {
     int i;
-    int encode, decode, jpeg;
-    DPY2TRACECTX(dpy);
+
+    DPY2TRACE_VIRCTX(dpy);
 
     TRACE_FUNCNAME(idx);
     
@@ -415,42 +1042,26 @@ void va_TraceCreateConfig(
     }
     va_TraceMsg(trace_ctx, NULL);
 
-    trace_ctx->trace_profile = profile;
-    trace_ctx->trace_entrypoint = entrypoint;
+    add_trace_config_info(pva_trace, *config_id, profile, entrypoint);
 
-    /* avoid to create so many empty files */
-    encode = (trace_ctx->trace_entrypoint == VAEntrypointEncSlice);
-    decode = (trace_ctx->trace_entrypoint == VAEntrypointVLD);
-    jpeg = (trace_ctx->trace_entrypoint == VAEntrypointEncPicture);
-    if ((encode && (trace_flag & VA_TRACE_FLAG_SURFACE_ENCODE)) ||
-        (decode && (trace_flag & VA_TRACE_FLAG_SURFACE_DECODE)) ||
-        (jpeg && (trace_flag & VA_TRACE_FLAG_SURFACE_JPEG))) {
-        FILE *tmp = fopen(trace_ctx->trace_surface_fn, "w");
-        
-        if (tmp)
-            trace_ctx->trace_fp_surface = tmp;
-        else {
-            va_errorMessage("Open file %s failed (%s)\n",
-                            trace_ctx->trace_surface_fn,
-                            strerror(errno));
-            trace_ctx->trace_fp_surface = NULL;
-            trace_flag &= ~(VA_TRACE_FLAG_SURFACE);
-        }
-    }
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
+}
 
-    if (encode && (trace_flag & VA_TRACE_FLAG_CODEDBUF)) {
-        FILE *tmp = fopen(trace_ctx->trace_codedbuf_fn, "w");
-        
-        if (tmp)
-            trace_ctx->trace_fp_codedbuf = tmp;
-        else {
-            va_errorMessage("Open file %s failed (%s)\n",
-                            trace_ctx->trace_codedbuf_fn,
-                            strerror(errno));
-            trace_ctx->trace_fp_codedbuf = NULL;
-            trace_flag &= ~VA_TRACE_FLAG_CODEDBUF;
-        }
-    }
+void va_TraceDestroyConfig (
+    VADisplay dpy,
+    VAConfigID config_id
+)
+{
+    DPY2TRACE_VIRCTX(dpy);
+
+    TRACE_FUNCNAME(idx);
+
+    va_TraceMsg(trace_ctx, "\tconfig = 0x%08x\n", config_id);
+    va_TraceMsg(trace_ctx, NULL);
+
+    delete_trace_config_info(pva_trace, config_id);
+
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
 }
 
 static void va_TraceSurfaceAttributes(
@@ -532,7 +1143,7 @@ void va_TraceCreateSurfaces(
 )
 {
     int i;
-    DPY2TRACECTX(dpy);
+    DPY2TRACE_VIRCTX(dpy);
 
     TRACE_FUNCNAME(idx);
     
@@ -549,8 +1160,9 @@ void va_TraceCreateSurfaces(
     va_TraceSurfaceAttributes(trace_ctx, attrib_list, &num_attribs);
 
     va_TraceMsg(trace_ctx, NULL);
-}
 
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
+}
 
 void va_TraceDestroySurfaces(
     VADisplay dpy,
@@ -559,7 +1171,7 @@ void va_TraceDestroySurfaces(
 )
 {
     int i;
-    DPY2TRACECTX(dpy);
+    DPY2TRACE_VIRCTX(dpy);
 
     TRACE_FUNCNAME(idx);
 
@@ -569,9 +1181,72 @@ void va_TraceDestroySurfaces(
     }
     
     va_TraceMsg(trace_ctx, NULL);
+
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
 }
 
 
+static void internal_TraceUpdateContext (
+    struct va_trace *pva_trace,
+    int tra_ctx_idx,
+    struct trace_context *new_trace_ctx,
+    VAContextID context,
+    int destroy_flag
+)
+{
+    struct trace_context *trace_ctx = NULL;
+    int i = 0, delete = 1;
+    pid_t thd_id = syscall(__NR_gettid);
+
+    if(tra_ctx_idx >= MAX_TRACE_CTX_NUM)
+        return;
+
+    LOCK_RESOURCE(pva_trace);
+
+    trace_ctx = pva_trace->ptra_ctx[tra_ctx_idx];
+    if(trace_ctx) {
+        if(!new_trace_ctx &&
+            trace_ctx->created_thd_id != thd_id
+            && !destroy_flag) {
+            delete = 0;
+        }
+        else {
+            pva_trace->context_num--;
+            pva_trace->ptra_ctx[tra_ctx_idx] = NULL;
+        }
+    }
+
+    if(new_trace_ctx) {
+        new_trace_ctx->created_thd_id = thd_id;
+        pva_trace->ptra_ctx[tra_ctx_idx] = new_trace_ctx;
+        pva_trace->context_num++;
+    }
+
+    UNLOCK_RESOURCE(pva_trace);
+
+    if(trace_ctx && delete) {
+        for(i = 0;i < MAX_TRACE_THREAD_NUM;i++)
+            if(trace_ctx->plog_file_list[i])
+                stop_tracing2log_file(pva_trace, trace_ctx->plog_file_list[i]);
+
+        if(trace_ctx->trace_codedbuf_fn)
+            free(trace_ctx->trace_codedbuf_fn);
+
+        if(trace_ctx->trace_fp_codedbuf)
+            fclose(trace_ctx->trace_fp_codedbuf);
+
+        if(trace_ctx->trace_surface_fn)
+            free(trace_ctx->trace_surface_fn);
+
+        if(trace_ctx->trace_fp_surface)
+            fclose(trace_ctx->trace_fp_surface);
+
+        //delete_trace_all_context_buf(pva_trace, context);
+
+        free(trace_ctx);
+    }
+}
+
 void va_TraceCreateContext(
     VADisplay dpy,
     VAConfigID config_id,
@@ -583,11 +1258,69 @@ void va_TraceCreateContext(
     VAContextID *context        /* out */
 )
 {
+    struct va_trace *pva_trace = NULL;
+    struct trace_context *trace_ctx = NULL;
+    int tra_ctx_id = 0;
+    int encode = 0, decode = 0, jpeg = 0;
     int i;
-    DPY2TRACECTX(dpy);
 
-    TRACE_FUNCNAME(idx);
+    pva_trace = (struct va_trace *)(((VADisplayContextP)dpy)->vatrace);
+    if(!context
+        || *context == VA_INVALID_ID
+        || !pva_trace) {
+        va_errorMessage("Invalid context id 0x%08x\n",
+                context == NULL ? 0 : (int)*context);
+        return;
+    }
+
+    LOCK_CONTEXT(pva_trace);
+
+    tra_ctx_id = get_free_ctx_idx(pva_trace, *context);
+    if(tra_ctx_id >= MAX_TRACE_CTX_NUM) {
+        va_errorMessage("Can't get trace context for ctx 0x%08x\n",
+                *context);
+        
+        goto FAIL;
+    }
+
+    trace_ctx = calloc(sizeof(struct trace_context), 1);
+    if(trace_ctx == NULL) {
+        va_errorMessage("Allocate trace context failed for ctx 0x%08x\n",
+                *context);
+        
+        goto FAIL;
+    }
 
+    i = get_valid_config_idx(pva_trace, config_id);
+    if(i >= MAX_TRACE_CTX_NUM) {
+        va_errorMessage("Can't get trace config id for ctx 0x%08x cfg %x\n",
+                *context, config_id);
+
+        goto FAIL;
+    }
+    trace_ctx->trace_profile = pva_trace->config_info[i].trace_profile;
+    trace_ctx->trace_entrypoint = pva_trace->config_info[i].trace_entrypoint;
+
+    if(trace_flag & VA_TRACE_FLAG_LOG) {
+        trace_ctx->plog_file = start_tracing2log_file(pva_trace);
+        if(!trace_ctx->plog_file) {
+            va_errorMessage("Can't get trace log file for ctx 0x%08x\n",
+                    *context);
+
+            goto FAIL;
+        }
+        else
+            va_infoMessage("Save context 0x%08x into log file %s\n", *context,
+                trace_ctx->plog_file->fn_log);
+
+        trace_ctx->plog_file_list[0] = trace_ctx->plog_file;
+    }
+
+    trace_ctx->trace_context = *context;
+    TRACE_FUNCNAME(idx);
+    va_TraceMsg(trace_ctx, "\tcontext = 0x%08x trace_flag 0x%x\n", *context, trace_flag);
+    va_TraceMsg(trace_ctx, "\tprofile = %d entrypoint = %d\n", trace_ctx->trace_profile,
+        trace_ctx->trace_entrypoint);
     va_TraceMsg(trace_ctx, "\tconfig = 0x%08x\n", config_id);
     va_TraceMsg(trace_ctx, "\twidth = %d\n", picture_width);
     va_TraceMsg(trace_ctx, "\theight = %d\n", picture_height);
@@ -597,12 +1330,7 @@ void va_TraceCreateContext(
         for (i=0; i<num_render_targets; i++)
             va_TraceMsg(trace_ctx, "\t\trender_targets[%d] = 0x%08x\n", i, render_targets[i]);
     }
-    if (context) {
-        va_TraceMsg(trace_ctx, "\tcontext = 0x%08x\n", *context);
-        trace_ctx->trace_context = *context;
-    } else
-        trace_ctx->trace_context = VA_INVALID_ID;
-    
+
     trace_ctx->trace_frame_no = 0;
     trace_ctx->trace_slice_no = 0;
 
@@ -613,8 +1341,74 @@ void va_TraceCreateContext(
         trace_ctx->trace_surface_width = picture_width;
     if (trace_ctx->trace_surface_height == 0)
         trace_ctx->trace_surface_height = picture_height;
+
+    /* avoid to create so many empty files */
+    encode = (trace_ctx->trace_entrypoint == VAEntrypointEncSlice);
+    decode = (trace_ctx->trace_entrypoint == VAEntrypointVLD);
+    jpeg = (trace_ctx->trace_entrypoint == VAEntrypointEncPicture);
+    if ((encode && (trace_flag & VA_TRACE_FLAG_SURFACE_ENCODE)) ||
+        (decode && (trace_flag & VA_TRACE_FLAG_SURFACE_DECODE)) ||
+        (jpeg && (trace_flag & VA_TRACE_FLAG_SURFACE_JPEG))) {
+        if(open_tracing_specil_file(pva_trace, trace_ctx, 1) < 0) {
+            va_errorMessage("Open surface fail failed for ctx 0x%08x\n", *context);
+
+            trace_flag &= ~(VA_TRACE_FLAG_SURFACE);
+        }
+    }
+
+    if (encode && (trace_flag & VA_TRACE_FLAG_CODEDBUF)) {
+        if(open_tracing_specil_file(pva_trace, trace_ctx, 0) < 0) {
+            va_errorMessage("Open codedbuf fail failed for ctx 0x%08x\n", *context);
+
+            trace_flag &= ~(VA_TRACE_FLAG_CODEDBUF);
+        }
+    }
+
+    internal_TraceUpdateContext(pva_trace, tra_ctx_id, trace_ctx, *context, 0);
+
+    UNLOCK_CONTEXT(pva_trace);
+    return;
+
+FAIL:
+    internal_TraceUpdateContext(pva_trace, tra_ctx_id, NULL, *context, 1);
+
+    UNLOCK_CONTEXT(pva_trace);
+
+    if(trace_ctx)
+        free(trace_ctx);
 }
 
+void va_TraceDestroyContext (
+    VADisplay dpy,
+    VAContextID context
+)
+{
+    struct va_trace *pva_trace = NULL;
+    struct trace_context *trace_ctx = NULL;
+    int ctx_id = 0;
+
+    pva_trace = (struct va_trace *)(((VADisplayContextP)dpy)->vatrace);
+
+    if(!pva_trace)
+        return;
+
+    LOCK_CONTEXT(pva_trace);
+
+    ctx_id = get_valid_ctx_idx(pva_trace, context);
+    if(ctx_id < MAX_TRACE_CTX_NUM) {
+        trace_ctx = pva_trace->ptra_ctx[ctx_id];
+
+        if(trace_ctx) {
+            refresh_log_file(pva_trace, trace_ctx);
+
+            internal_TraceUpdateContext(pva_trace,
+                get_valid_ctx_idx(pva_trace, context),
+                NULL, context, 0);
+        }
+    }
+
+    UNLOCK_CONTEXT(pva_trace);
+}
 
 static char * buffer_type_to_string(int type)
 {
@@ -657,7 +1451,9 @@ void va_TraceCreateBuffer (
     VABufferID *buf_id		/* out */
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
+
+    add_trace_buf_info(pva_trace, context, *buf_id);
 
     /* only trace CodedBuffer */
     if (type != VAEncCodedBufferType)
@@ -685,10 +1481,12 @@ void va_TraceDestroyBuffer (
     VACodedBufferSegment *buf_list;
     int i = 0;
     
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, VA_INVALID_ID, buf_id);
 
     vaBufferInfo(dpy, trace_ctx->trace_context, buf_id, &type, &size, &num_elements);    
-    
+
+    delete_trace_buf_info(pva_trace, buf_id);
+
     /* only trace CodedBuffer */
     if (type != VAEncCodedBufferType)
         return;
@@ -753,6 +1551,8 @@ static void va_TraceCodedBufferIVFHeader(struct trace_context *trace_ctx, void *
     mem_put_le32(header+8, 0);
     fwrite(header, 1, 12, trace_ctx->trace_fp_codedbuf);
     trace_ctx->pts++;
+
+    fflush(trace_ctx->trace_fp_codedbuf);
 }
 
 void va_TraceMapBuffer (
@@ -767,11 +1567,11 @@ void va_TraceMapBuffer (
     
     VACodedBufferSegment *buf_list;
     int i = 0;
-    
-    DPY2TRACECTX(dpy);
+
+    DPY2TRACECTX(dpy, VA_INVALID_ID, buf_id);
 
     vaBufferInfo(dpy, trace_ctx->trace_context, buf_id, &type, &size, &num_elements);    
-    
+
     /* only trace CodedBuffer */
     if (type != VAEncCodedBufferType)
         return;
@@ -800,6 +1600,8 @@ void va_TraceMapBuffer (
         if (trace_ctx->trace_fp_codedbuf) {
             va_TraceMsg(trace_ctx, "\tDump the content to file\n");
             fwrite(buf_list->buf, buf_list->size, 1, trace_ctx->trace_fp_codedbuf);
+
+            fflush(trace_ctx->trace_fp_codedbuf);
         }
         
         buf_list = buf_list->next;
@@ -819,23 +1621,27 @@ static void va_TraceVABuffers(
 {
     unsigned int i;
     unsigned char *p = pbuf;
+    FILE *fp = NULL;
 
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     
-    va_TraceMsg(trace_ctx, "--%s\n",  buffer_type_to_string(type));
+    va_TraceMsg(trace_ctx, "--%s\n", buffer_type_to_string(type));
 
-    if ((trace_flag & VA_TRACE_FLAG_BUFDATA) && trace_ctx->trace_fp_log) {
+    if(trace_ctx->plog_file)
+        fp = trace_ctx->plog_file->fp_log;
+
+    if ((trace_flag & VA_TRACE_FLAG_BUFDATA) && fp) {
         for (i=0; i<size; i++) {
             unsigned char value =  p[i];
 
             if (i==0)
-                fprintf(trace_ctx->trace_fp_log, "\t\t0x%04x:", i);
+                fprintf(fp, "\t\t0x%04x:", i);
             else if ((i%16) == 0)
-                fprintf(trace_ctx->trace_fp_log, "\n\t\t0x%04x:", i);
+                fprintf(fp, "\n\t\t0x%04x:", i);
 
-            fprintf(trace_ctx->trace_fp_log, " %02x", value);
+            fprintf(fp, " %02x", value);
         }
-        fprintf(trace_ctx->trace_fp_log, "\n");
+        fprintf(fp, "\n");
     }
     
     va_TraceMsg(trace_ctx, NULL);
@@ -854,7 +1660,7 @@ static void va_TraceVAPictureParameterBufferMPEG2(
     void *data)
 {
     VAPictureParameterBufferMPEG2 *p=(VAPictureParameterBufferMPEG2 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     va_TraceMsg(trace_ctx,"VAPictureParameterBufferMPEG2\n");
 
@@ -893,7 +1699,7 @@ static void va_TraceVAIQMatrixBufferMPEG2(
     void *data)
 {
     VAIQMatrixBufferMPEG2 *p=(VAIQMatrixBufferMPEG2 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     va_TraceMsg(trace_ctx,"VAIQMatrixBufferMPEG2\n");
 
@@ -922,7 +1728,7 @@ static void va_TraceVASliceParameterBufferMPEG2(
 {
     VASliceParameterBufferMPEG2 *p=(VASliceParameterBufferMPEG2 *)data;
 
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     trace_ctx->trace_slice_no++;
     
@@ -954,7 +1760,7 @@ static void va_TraceVAPictureParameterBufferJPEG(
 {
     int i;
     VAPictureParameterBufferJPEGBaseline *p=(VAPictureParameterBufferJPEGBaseline *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     va_TraceMsg(trace_ctx,"*VAPictureParameterBufferJPEG\n");
     va_TraceMsg(trace_ctx,"\tpicture_width = %u\n", p->picture_width);
@@ -980,7 +1786,7 @@ static void va_TraceVAIQMatrixBufferJPEG(
     int i, j;
     static char tmp[1024];
     VAIQMatrixBufferJPEGBaseline *p=(VAIQMatrixBufferJPEGBaseline *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     va_TraceMsg(trace_ctx,"*VAIQMatrixParameterBufferJPEG\n");
     va_TraceMsg(trace_ctx,"\tload_quantiser_table =\n");
     for (i = 0; i < 4; ++i) {
@@ -1007,7 +1813,7 @@ static void va_TraceVASliceParameterBufferJPEG(
 {
     int i;
     VASliceParameterBufferJPEGBaseline *p=(VASliceParameterBufferJPEGBaseline *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     va_TraceMsg(trace_ctx,"*VASliceParameterBufferJPEG\n");
     va_TraceMsg(trace_ctx,"\tslice_data_size = %u\n", p->slice_data_size);
     va_TraceMsg(trace_ctx,"\tslice_data_offset = %u\n", p->slice_data_offset);
@@ -1036,7 +1842,7 @@ static void va_TraceVAHuffmanTableBufferJPEG(
     int i, j;
     static char tmp[1024];
     VAHuffmanTableBufferJPEGBaseline *p=(VAHuffmanTableBufferJPEGBaseline *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     va_TraceMsg(trace_ctx,"*VAHuffmanTableBufferJPEG\n");
 
     for (i = 0; i < 2; ++i) {
@@ -1082,7 +1888,7 @@ static void va_TraceVAPictureParameterBufferMPEG4(
     int i;
     VAPictureParameterBufferMPEG4 *p=(VAPictureParameterBufferMPEG4 *)data;
     
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     va_TraceMsg(trace_ctx,"*VAPictureParameterBufferMPEG4\n");
     va_TraceMsg(trace_ctx,"\tvop_width = %d\n", p->vop_width);
@@ -1141,7 +1947,7 @@ static void va_TraceVAIQMatrixBufferMPEG4(
 {
     int i;
     VAIQMatrixBufferMPEG4 *p=(VAIQMatrixBufferMPEG4 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     va_TraceMsg(trace_ctx,"VAIQMatrixBufferMPEG4\n");
 
@@ -1169,7 +1975,7 @@ static void va_TraceVAEncSequenceParameterBufferMPEG4(
     void *data)
 {
     VAEncSequenceParameterBufferMPEG4 *p = (VAEncSequenceParameterBufferMPEG4 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     
     va_TraceMsg(trace_ctx, "\t--VAEncSequenceParameterBufferMPEG4\n");
     
@@ -1199,7 +2005,7 @@ static void va_TraceVAEncPictureParameterBufferMPEG4(
     void *data)
 {
     VAEncPictureParameterBufferMPEG4 *p = (VAEncPictureParameterBufferMPEG4 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     
     va_TraceMsg(trace_ctx, "\t--VAEncPictureParameterBufferMPEG4\n");
     va_TraceMsg(trace_ctx, "\treference_picture = 0x%08x\n", p->reference_picture);
@@ -1227,7 +2033,7 @@ static void va_TraceVASliceParameterBufferMPEG4(
 {
     VASliceParameterBufferMPEG4 *p=(VASliceParameterBufferMPEG4 *)data;
     
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     trace_ctx->trace_slice_no++;
 
@@ -1271,7 +2077,7 @@ static void va_TraceVAPictureParameterBufferHEVC(
     int i;
     VAPictureParameterBufferHEVC *p = (VAPictureParameterBufferHEVC*)data;
 
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     va_TraceMsg(trace_ctx, "VAPictureParameterBufferHEVC\n");
 
@@ -1397,7 +2203,7 @@ static void va_TraceVASliceParameterBufferHEVC(
     int i,j;
     VASliceParameterBufferHEVC* p = (VASliceParameterBufferHEVC*)data;
 
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     trace_ctx->trace_slice_no++;
     trace_ctx->trace_slice_size = p->slice_data_size;
@@ -1484,7 +2290,7 @@ static void va_TraceVAIQMatrixBufferHEVC(
     int i, j;
     VAIQMatrixBufferHEVC* p = (VAIQMatrixBufferHEVC* )data;
 
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     va_TraceMsg(trace_ctx, "VAIQMatrixBufferHEVC\n");
 
@@ -1547,7 +2353,7 @@ static void va_TraceVAEncSequenceParameterBufferHEVC(
 {
     VAEncSequenceParameterBufferHEVC *p = (VAEncSequenceParameterBufferHEVC *)data;
 
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     if(!p)
         return;
@@ -1620,7 +2426,7 @@ static void va_TraceVAEncPictureParameterBufferHEVC(
     int i;
     VAEncPictureParameterBufferHEVC *p = (VAEncPictureParameterBufferHEVC *)data;
 
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     if(!p)
         return;
@@ -1700,7 +2506,7 @@ static void va_TraceVAEncSliceParameterBufferHEVC(
     int i;
     VAEncSliceParameterBufferHEVC *p = (VAEncSliceParameterBufferHEVC *)data;
 
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     if(!p)
         return;
@@ -1789,7 +2595,7 @@ static void va_TraceVAPictureParameterBufferH264(
     int i;
     VAPictureParameterBufferH264 *p = (VAPictureParameterBufferH264*)data;
     
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     va_TraceMsg(trace_ctx, "\t--VAPictureParameterBufferH264\n");
 
@@ -1860,7 +2666,7 @@ static void va_TraceVASliceParameterBufferH264(
 {
     int i;
     VASliceParameterBufferH264* p = (VASliceParameterBufferH264*)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     trace_ctx->trace_slice_no++;
     trace_ctx->trace_slice_size = p->slice_data_size;
@@ -1954,18 +2760,22 @@ static void va_TraceVAIQMatrixBufferH264(
 {
     int i, j;
     VAIQMatrixBufferH264* p = (VAIQMatrixBufferH264* )data;
+    FILE *fp = NULL;
+
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
-    DPY2TRACECTX(dpy);
+    if(trace_ctx->plog_file)
+        fp = trace_ctx->plog_file->fp_log;
 
     va_TraceMsg(trace_ctx, "\t--VAIQMatrixBufferH264\n");
 
     va_TraceMsg(trace_ctx, "\tScalingList4x4[6][16]=\n");
     for (i = 0; i < 6; i++) {
         for (j = 0; j < 16; j++) {
-            if (trace_ctx->trace_fp_log) {
-                fprintf(trace_ctx->trace_fp_log, "\t%d", p->ScalingList4x4[i][j]);
+            if (fp) {
+                fprintf(fp, "\t%d", p->ScalingList4x4[i][j]);
                 if ((j + 1) % 8 == 0)
-                    fprintf(trace_ctx->trace_fp_log, "\n");
+                    fprintf(fp, "\n");
             }
         }
     }
@@ -1973,10 +2783,10 @@ static void va_TraceVAIQMatrixBufferH264(
     va_TraceMsg(trace_ctx, "\tScalingList8x8[2][64]=\n");
     for (i = 0; i < 2; i++) {
         for (j = 0; j < 64; j++) {
-            if (trace_ctx->trace_fp_log) {
-                fprintf(trace_ctx->trace_fp_log,"\t%d", p->ScalingList8x8[i][j]);
+            if (fp) {
+                fprintf(fp,"\t%d", p->ScalingList8x8[i][j]);
                 if ((j + 1) % 8 == 0)
-                    fprintf(trace_ctx->trace_fp_log, "\n");
+                    fprintf(fp, "\n");
             }
         }
     }
@@ -1996,7 +2806,7 @@ static void va_TraceVAEncSequenceParameterBufferH264(
     void *data)
 {
     VAEncSequenceParameterBufferH264 *p = (VAEncSequenceParameterBufferH264 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     unsigned int i;
 
     va_TraceMsg(trace_ctx, "\t--VAEncSequenceParameterBufferH264\n");
@@ -2059,7 +2869,7 @@ static void va_TraceVAEncPictureParameterBufferH264(
     void *data)
 {
     VAEncPictureParameterBufferH264 *p = (VAEncPictureParameterBufferH264 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     int i;
 
     va_TraceMsg(trace_ctx, "\t--VAEncPictureParameterBufferH264\n");
@@ -2122,7 +2932,7 @@ static void va_TraceVAEncSliceParameterBuffer(
     void *data)
 {
     VAEncSliceParameterBuffer* p = (VAEncSliceParameterBuffer*)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     
     va_TraceMsg(trace_ctx, "\t--VAEncSliceParameterBuffer\n");
     
@@ -2147,7 +2957,7 @@ static void va_TraceVAEncSliceParameterBufferH264(
     void *data)
 {
     VAEncSliceParameterBufferH264* p = (VAEncSliceParameterBufferH264*)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     int i;
 
     if (!p)
@@ -2265,7 +3075,7 @@ static void va_TraceVAEncPackedHeaderParameterBufferType(
     void *data)
 {
     VAEncPackedHeaderParameterBuffer* p = (VAEncPackedHeaderParameterBuffer*)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     int i;
 
     if (!p)
@@ -2289,7 +3099,7 @@ static void va_TraceVAEncMiscParameterBuffer(
     void *data)
 {
     VAEncMiscParameterBuffer* tmp = (VAEncMiscParameterBuffer*)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     
     switch (tmp->type) {
     case VAEncMiscParameterTypeFrameRate:
@@ -2373,7 +3183,7 @@ static void va_TraceVAPictureParameterBufferVC1(
 )
 {
     VAPictureParameterBufferVC1* p = (VAPictureParameterBufferVC1*)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     
     va_TraceMsg(trace_ctx, "\t--VAPictureParameterBufferVC1\n");
     
@@ -2478,7 +3288,7 @@ static void va_TraceVASliceParameterBufferVC1(
 )
 {
     VASliceParameterBufferVC1 *p = (VASliceParameterBufferVC1*)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     trace_ctx->trace_slice_no++;
     trace_ctx->trace_slice_size = p->slice_data_size;
@@ -2503,7 +3313,7 @@ static void va_TraceVAPictureParameterBufferVP8(
 {
     char tmp[1024];
     VAPictureParameterBufferVP8 *p = (VAPictureParameterBufferVP8 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     int i,j;
 
     va_TraceMsg(trace_ctx, "\t--VAPictureParameterBufferVP8\n");
@@ -2578,7 +3388,7 @@ static void va_TraceVASliceParameterBufferVP8(
     void *data)
 {
     VASliceParameterBufferVP8 *p = (VASliceParameterBufferVP8 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     int i;
 
     va_TraceMsg(trace_ctx, "\t--VASliceParameterBufferVP8\n");
@@ -2608,7 +3418,7 @@ static void va_TraceVAIQMatrixBufferVP8(
 {
     char tmp[1024];
     VAIQMatrixBufferVP8 *p = (VAIQMatrixBufferVP8 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     int i,j;
 
     va_TraceMsg(trace_ctx, "\t--VAIQMatrixBufferVP8\n");
@@ -2636,7 +3446,7 @@ static void va_TraceVAProbabilityBufferVP8(
 {
     char tmp[1024];
     VAProbabilityDataBufferVP8 *p = (VAProbabilityDataBufferVP8 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     int i,j,k,l;
 
     va_TraceMsg(trace_ctx, "\t--VAProbabilityDataBufferVP8\n");
@@ -2665,7 +3475,7 @@ static void va_TraceVAEncSequenceParameterBufferVP8(
     void *data)
 {
     VAEncSequenceParameterBufferVP8 *p = (VAEncSequenceParameterBufferVP8 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     int i;
 
     va_TraceMsg(trace_ctx, "\t--VAEncSequenceParameterBufferVP8\n");
@@ -2699,7 +3509,7 @@ static void va_TraceVAPictureParameterBufferVP9(
     void *data)
 {
     VADecPictureParameterBufferVP9 *p = (VADecPictureParameterBufferVP9 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     int i,j;
 
     va_TraceMsg(trace_ctx, "\t--VAPictureParameterBufferVP9\n");
@@ -2765,7 +3575,7 @@ static void va_TraceVAEncPictureParameterBufferVP8(
     void *data)
 {
     VAEncPictureParameterBufferVP8 *p = (VAEncPictureParameterBufferVP8 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     int i;
 
     va_TraceMsg(trace_ctx, "\t--VAEncPictureParameterBufferVP8\n");
@@ -2834,7 +3644,7 @@ static void va_TraceVASliceParameterBufferVP9(
 {
 
     VASliceParameterBufferVP9 *p = (VASliceParameterBufferVP9 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     int i, j;
 
     va_TraceMsg(trace_ctx, "\t--VASliceParameterBufferVP9\n");
@@ -2870,7 +3680,7 @@ void va_TraceBeginPicture(
     VASurfaceID render_target
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     TRACE_FUNCNAME(idx);
 
@@ -2951,7 +3761,7 @@ static void va_TraceVAEncSequenceParameterBufferH263(
     void *data)
 {
     VAEncSequenceParameterBufferH263 *p = (VAEncSequenceParameterBufferH263 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     
     va_TraceMsg(trace_ctx, "\t--VAEncSequenceParameterBufferH263\n");
     
@@ -2976,7 +3786,7 @@ static void va_TraceVAEncPictureParameterBufferH263(
     void *data)
 {
     VAEncPictureParameterBufferH263 *p = (VAEncPictureParameterBufferH263 *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     
     va_TraceMsg(trace_ctx, "\t--VAEncPictureParameterBufferH263\n");
     va_TraceMsg(trace_ctx, "\treference_picture = 0x%08x\n", p->reference_picture);
@@ -3002,7 +3812,7 @@ static void va_TraceVAEncPictureParameterBufferJPEG(
     VAEncPictureParameterBufferJPEG *p = (VAEncPictureParameterBufferJPEG *)data;
     int i;
     
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     
     va_TraceMsg(trace_ctx, "\t--VAEncPictureParameterBufferJPEG\n");
     va_TraceMsg(trace_ctx, "\treconstructed_picture = 0x%08x\n", p->reconstructed_picture);
@@ -3044,7 +3854,7 @@ static void va_TraceVAEncQMatrixBufferJPEG(
     void *data)
 {
     VAQMatrixBufferJPEG *p = (VAQMatrixBufferJPEG *)data;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     
     va_TraceMsg(trace_ctx, "\t--VAQMatrixBufferJPEG\n");
     va_TraceMsg(trace_ctx, "\tload_lum_quantiser_matrix = %d", p->load_lum_quantiser_matrix);
@@ -3086,7 +3896,7 @@ static void va_TraceVAEncSliceParameterBufferJPEG(
     VAEncSliceParameterBufferJPEG *p = (VAEncSliceParameterBufferJPEG *)data;
     int i;
     
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     
     va_TraceMsg(trace_ctx, "\t--VAEncSliceParameterBufferJPEG\n");
     va_TraceMsg(trace_ctx, "\trestart_interval = 0x%04x\n", p->restart_interval);
@@ -3286,7 +4096,7 @@ static void va_TraceHEVCBuf(
     void *pbuf
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     switch (type) {
         case VAPictureParameterBufferType:
@@ -3326,7 +4136,7 @@ static void va_TraceH264Buf(
     void *pbuf
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
     
     switch (type) {
     case VAPictureParameterBufferType:
@@ -3398,7 +4208,7 @@ static void va_TraceVP8Buf(
     void *pbuf
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     switch (type) {
     case VAPictureParameterBufferType:
@@ -3462,7 +4272,7 @@ static void va_TraceVP9Buf(
     void *pbuf
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     switch (type) {
     case VAPictureParameterBufferType:
@@ -3487,7 +4297,7 @@ static void va_TraceVC1Buf(
     void *pbuf
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     switch (type) {
     case VAPictureParameterBufferType:
@@ -3547,7 +4357,7 @@ va_TraceProcFilterParameterBufferDeinterlacing(
 {
     VAProcFilterParameterBufferDeinterlacing *deint = (VAProcFilterParameterBufferDeinterlacing *)base;
 
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     va_TraceMsg(trace_ctx, "\t    type = %d\n", deint->type);
     va_TraceMsg(trace_ctx, "\t    algorithm = %d\n", deint->algorithm);
@@ -3563,7 +4373,7 @@ va_TraceProcFilterParameterBufferColorBalance(
 {
     VAProcFilterParameterBufferColorBalance *color_balance = (VAProcFilterParameterBufferColorBalance *)base;
 
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     va_TraceMsg(trace_ctx, "\t    type = %d\n", color_balance->type);
     va_TraceMsg(trace_ctx, "\t    attrib = %d\n", color_balance->attrib);
@@ -3577,7 +4387,7 @@ va_TraceProcFilterParameterBufferBase(
     VAProcFilterParameterBufferBase *base
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     va_TraceMsg(trace_ctx, "\t    type = %d\n", base->type);
 }
@@ -3596,7 +4406,7 @@ va_TraceProcFilterParameterBuffer(
     VAProcFilterParameterBufferBase *base_filter = NULL;
     int i;
 
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     if (num_filters == 0 || filters == NULL) {
         va_TraceMsg(trace_ctx, "\t  num_filters = %d\n", num_filters);
@@ -3661,7 +4471,7 @@ va_TraceVAProcPipelineParameterBuffer(
     VAProcPipelineParameterBuffer *p = (VAProcPipelineParameterBuffer *)data;
     int i;
 
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     va_TraceMsg(trace_ctx, "\t--VAProcPipelineParameterBuffer\n");
 
@@ -3746,7 +4556,7 @@ va_TraceNoneBuf(
     void *pbuf
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     switch (type) {
     case VAProcPipelineParameterBufferType:
@@ -3769,7 +4579,7 @@ void va_TraceRenderPicture(
     unsigned int size;
     unsigned int num_elements;
     int i;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     TRACE_FUNCNAME(idx);
     
@@ -3893,7 +4703,7 @@ void va_TraceEndPicture(
 )
 {
     int encode, decode, jpeg;
-    DPY2TRACECTX(dpy);
+    DPY2TRACECTX(dpy, context, VA_INVALID_ID);
 
     TRACE_FUNCNAME(idx);
 
@@ -3908,12 +4718,12 @@ void va_TraceEndPicture(
     /* trace encode source surface, can do it before HW completes rendering */
     if ((encode && (trace_flag & VA_TRACE_FLAG_SURFACE_ENCODE))||
         (jpeg && (trace_flag & VA_TRACE_FLAG_SURFACE_JPEG)))
-        va_TraceSurface(dpy);
+        va_TraceSurface(dpy, context);
     
     /* trace decoded surface, do it after HW completes rendering */
     if (decode && ((trace_flag & VA_TRACE_FLAG_SURFACE_DECODE))) {
         vaSyncSurface(dpy, trace_ctx->trace_rendertarget);
-        va_TraceSurface(dpy);
+        va_TraceSurface(dpy, context);
     }
 
     va_TraceMsg(trace_ctx, NULL);
@@ -3925,12 +4735,14 @@ void va_TraceSyncSurface(
     VASurfaceID render_target
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACE_VIRCTX(dpy);
 
     TRACE_FUNCNAME(idx);
 
     va_TraceMsg(trace_ctx, "\trender_target = 0x%08x\n", render_target);
     va_TraceMsg(trace_ctx, NULL);
+
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
 }
 
 void va_TraceQuerySurfaceAttributes(
@@ -3940,7 +4752,7 @@ void va_TraceQuerySurfaceAttributes(
     unsigned int       *num_attribs
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACE_VIRCTX(dpy);
 
     TRACE_FUNCNAME(idx);
     va_TraceMsg(trace_ctx, "\tconfig = 0x%08x\n", config);
@@ -3948,6 +4760,7 @@ void va_TraceQuerySurfaceAttributes(
     
     va_TraceMsg(trace_ctx, NULL);
 
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
 }
 
 
@@ -3957,7 +4770,7 @@ void va_TraceQuerySurfaceStatus(
     VASurfaceStatus *status    /* out */
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACE_VIRCTX(dpy);
 
     TRACE_FUNCNAME(idx);
 
@@ -3965,6 +4778,8 @@ void va_TraceQuerySurfaceStatus(
     if (status)
         va_TraceMsg(trace_ctx, "\tstatus = 0x%08x\n", *status);
     va_TraceMsg(trace_ctx, NULL);
+
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
 }
 
 
@@ -3975,7 +4790,7 @@ void va_TraceQuerySurfaceError(
     void **error_info       /*out*/
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACE_VIRCTX(dpy);
 
     TRACE_FUNCNAME(idx);
     va_TraceMsg(trace_ctx, "\tsurface = 0x%08x\n", surface);
@@ -3990,6 +4805,8 @@ void va_TraceQuerySurfaceError(
         }
     }
     va_TraceMsg(trace_ctx, NULL);
+
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
 }
 
 void va_TraceMaxNumDisplayAttributes (
@@ -3997,12 +4814,14 @@ void va_TraceMaxNumDisplayAttributes (
     int number
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACE_VIRCTX(dpy);
 
     TRACE_FUNCNAME(idx);
     
     va_TraceMsg(trace_ctx, "\tmax_display_attributes = %d\n", number);
     va_TraceMsg(trace_ctx, NULL);
+
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
 }
 
 void va_TraceQueryDisplayAttributes (
@@ -4012,12 +4831,12 @@ void va_TraceQueryDisplayAttributes (
 )
 {
     int i;
-    
-    DPY2TRACECTX(dpy);
-    
+
     if (attr_list == NULL || num_attributes == NULL)
         return;
 
+    DPY2TRACE_VIRCTX(dpy);
+
     va_TraceMsg(trace_ctx, "\tnum_attributes = %d\n", *num_attributes);
     
     for (i=0; i<*num_attributes; i++) {
@@ -4029,23 +4848,24 @@ void va_TraceQueryDisplayAttributes (
         va_TraceMsg(trace_ctx, "\t  flags = %d\n", attr_list[i].flags);
     }
     va_TraceMsg(trace_ctx, NULL);
+
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
 }
 
 
 static void va_TraceDisplayAttributes (
-    VADisplay dpy,
+    struct trace_context *trace_ctx,
     VADisplayAttribute *attr_list,
     int num_attributes
 )
 {
     int i;
-    
-    DPY2TRACECTX(dpy);
-    
-    va_TraceMsg(trace_ctx, "\tnum_attributes = %d\n", num_attributes);
+
     if (attr_list == NULL)
         return;
-    
+
+    va_TraceMsg(trace_ctx, "\tnum_attributes = %d\n", num_attributes);
+
     for (i=0; i<num_attributes; i++) {
         va_TraceMsg(trace_ctx, "\tattr_list[%d] =\n");
         va_TraceMsg(trace_ctx, "\t  typ = 0x%08x\n", attr_list[i].type);
@@ -4064,11 +4884,13 @@ void va_TraceGetDisplayAttributes (
     int num_attributes
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACE_VIRCTX(dpy);
 
     TRACE_FUNCNAME(idx);
 
-    va_TraceDisplayAttributes (dpy, attr_list, num_attributes);
+    va_TraceDisplayAttributes (trace_ctx, attr_list, num_attributes);
+
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
 }
 
 void va_TraceSetDisplayAttributes (
@@ -4077,11 +4899,13 @@ void va_TraceSetDisplayAttributes (
     int num_attributes
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACE_VIRCTX(dpy);
 
     TRACE_FUNCNAME(idx);
 
-    va_TraceDisplayAttributes (dpy, attr_list, num_attributes);
+    va_TraceDisplayAttributes (trace_ctx, attr_list, num_attributes);
+
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
 }
 
 
@@ -4102,7 +4926,7 @@ void va_TracePutSurface (
     unsigned int flags /* de-interlacing flags */
 )
 {
-    DPY2TRACECTX(dpy);
+    DPY2TRACE_VIRCTX(dpy);
 
     TRACE_FUNCNAME(idx);
     
@@ -4120,4 +4944,6 @@ void va_TracePutSurface (
     va_TraceMsg(trace_ctx, "\tnumber_cliprects = %d\n", number_cliprects);
     va_TraceMsg(trace_ctx, "\tflags = 0x%08x\n", flags);
     va_TraceMsg(trace_ctx, NULL);
+
+    DPY2TRACE_VIRCTX_EXIT(pva_trace);
 }
diff --git a/va/va_trace.h b/va/va_trace.h
index 141e7c3..5b320c6 100644
--- a/va/va_trace.h
+++ b/va/va_trace.h
@@ -78,6 +78,12 @@ void va_TraceCreateConfig(
 );
 
 DLL_HIDDEN
+void va_TraceDestroyConfig (
+    VADisplay dpy,
+    VAConfigID config_id
+);
+
+DLL_HIDDEN
 void va_TraceCreateSurfaces(
     VADisplay dpy,
     int width,
@@ -109,6 +115,12 @@ void va_TraceCreateContext(
 );
 
 DLL_HIDDEN
+void va_TraceDestroyContext (
+    VADisplay dpy,
+    VAContextID context
+);
+
+DLL_HIDDEN
 void va_TraceCreateBuffer (
     VADisplay dpy,
     VAContextID context,	/* in */
-- 
1.9.1

_______________________________________________
Libva mailing list
Libva at lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/libva


More information about the Libva mailing list