You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

231 lines
8.0 KiB

/*
* Copyright (c) Hisilicon Technologies Co., Ltd.. 2018-2019. All rights reserved.
* Description: Gralloc
* Author: Hisilicon
* Created: 2019.11.07
*/
#include "gralloc_debug.h"
#include <inttypes.h>
#include <fcntl.h>
#include <vector>
#include <securec.h>
#include <cutils/properties.h>
#include <hardware/hardware.h>
#include "mali_gralloc_formats.h"
static bool g_debug_dump_enable = false;
static bool g_debug_capture_enable = false;
static pthread_mutex_t g_ionbuffer_dump_lock = PTHREAD_MUTEX_INITIALIZER;
static pthread_mutex_t g_frambuffer_dump_lock = PTHREAD_MUTEX_INITIALIZER;
static void gralloc_dump_string(android::String8 &buf, const char *fmt, ...)
{
va_list args;
va_start(args, fmt);
buf.appendFormatV(fmt, args);
va_end(args);
}
static int gralloc_debug_pid2name(pid_t pid, char *process_name, int name_len)
{
ssize_t size;
if (pid < 0) {
ALOGE("Invalid pid %d and return", pid);
return GRALLOC_FAILURE;
}
sprintf_s(process_name, name_len, "/proc/%d/cmdline", pid);
int fd = open(process_name, O_RDONLY);
if (fd == -1) {
return GRALLOC_FAILURE;
}
size = read(fd, process_name, name_len);
if (size > 0) {
process_name[size] = '\0';
}
close(fd);
return GRALLOC_SUCCESS;
}
void gralloc_debug_dump_ionbuffer(const private_internal_handle_t *handle, bool is_retain)
{
android::String8 dump_strings;
char process_name[PATH_MAX];
int ret;
if (handle == nullptr) {
GRALLOC_ERROR_INFO();
return;
}
ret = gralloc_debug_pid2name(getpid(), process_name, PATH_MAX - 1);
if (ret == GRALLOC_FAILURE) {
return;
}
pthread_mutex_lock(&g_ionbuffer_dump_lock);
gralloc_dump_string(dump_strings,
"---------------------[%s] dump gralloc ionbuffer info start: ------------------------\n",
is_retain ? "retain " : "release");
gralloc_dump_string(dump_strings,
"---------------------process name : %s------------------------\n", process_name);
gralloc_dump_string(dump_strings,
" handle | addr | width | height |pixel_stride|bytes_stride|"
" size | format |internal format|consumer usage|producer usage| fd | AFBC |\n");
gralloc_dump_string(dump_strings,
"------------+------------+-------+--------+------------+------------+"
"----------+----------+---------------+--------------+--------------+-----------+------+\n");
gralloc_dump_string(dump_strings,
" %010" PRIxPTR " | %010" PRIxPTR " | %5d | %5d | %5d | %5d |"
" %8d | %08x | %09" PRIx64 " | %09" PRIx64 " | %09" PRIx64 " | %08x | %4d |\n",
handle, handle->addr, handle->width, handle->height, handle->pixel_stride,
handle->bytes_stride, handle->size, handle->format, handle->internal_format,
handle->consumer_usage, handle->producer_usage, handle->fd,
((handle->internal_format & MALI_GRALLOC_INTFMT_AFBCENABLE_MASK) != 0) ? true : false);
gralloc_dump_string(dump_strings,
"-------------------------dump gralloc ionbuffer info end :------------------------\n");
pthread_mutex_unlock(&g_ionbuffer_dump_lock);
ALOGD("%s", dump_strings.string());
}
void gralloc_debug_capture_ionbuffer(const private_internal_handle_t *handle)
{
char file_path[PATH_MAX];
char real_path[PATH_MAX];
char process_path_name[PATH_MAX];
android::String8 string8_name;
static int count = 0;
int fd;
int ret;
pid_t pid;
int len;
if (handle == nullptr || handle->base == nullptr) {
GRALLOC_ERROR_INFO();
return;
}
pid = getpid();
ret = gralloc_debug_pid2name(pid, process_path_name, PATH_MAX - 1);
if (ret == GRALLOC_FAILURE) {
return;
}
string8_name = android::String8(process_path_name, PATH_MAX);
if (realpath(DUMP_CAPTURE_DIR, real_path) == nullptr) {
return;
}
len = snprintf_s(file_path, PATH_MAX, PATH_MAX - 1, "%s/process-%s_pid-%d_format-%d_w-%d_h-%d_stride-%d_count-%d",
real_path, string8_name.getPathLeaf().string(), pid, handle->format,
handle->width, handle->height, handle->pixel_stride, count++);
if (len < 0) {
GRALLOC_ERROR_INFO();
return;
}
fd = open(file_path, O_WRONLY | O_CREAT | O_TRUNC, 0644); /* 0644: rw,r,r */
if (fd != -1) {
write(fd, (void *)handle->base, handle->size);
close(fd);
}
ALOGD("gralloc capture ionbuffer finish");
}
void gralloc_debug_dump_framebuffer(const private_internal_handle_t *handle, const private_module_t *m)
{
android::String8 dump_strings;
char process_name[PATH_MAX];
int ret;
unsigned int id;
if (handle == nullptr || m == nullptr) {
GRALLOC_ERROR_INFO();
return;
}
ret = gralloc_debug_pid2name(getpid(), process_name, PATH_MAX - 1);
if (ret == GRALLOC_FAILURE) {
return;
}
pthread_mutex_lock(&g_frambuffer_dump_lock);
id = (reinterpret_cast<const hw_module_t *>(m))->reserved[0];
gralloc_dump_string(dump_strings,
"-------------------------dump gralloc framebuffer info start :------------------------\n");
gralloc_dump_string(dump_strings, " handle | address | width | height | internal width | internal height |"
" stride | format |internal format|consumer usage|producer usage| fd | AFBC |\n");
gralloc_dump_string(dump_strings,
"----------+----------+-------+--------+----------------+-----------------+--------+"
"----------+---------------+--------------+--------------+----------+------+\n");
gralloc_dump_string(dump_strings,
" %08" PRIxPTR " | %08" PRIxPTR " | %5d | %5d | %5d | %5d | %5d |"
" %08x | %09" PRIx64 " | %09" PRIx64 " | %09" PRIx64 " | %08x | %4d |\n",
handle, handle->addr, handle->width, handle->height,
handle->internal_width, handle->internal_height, handle->pixel_stride,
handle->format, handle->internal_format,
handle->consumer_usage, handle->producer_usage, handle->fd,
((handle->internal_format & MALI_GRALLOC_INTFMT_AFBCENABLE_MASK) != 0) ? true : false);
gralloc_dump_string(dump_strings, "---------------------------------------------------------------------\n");
gralloc_dump_string(dump_strings, " fb | xres | yres | xdpi | ydpi | fps | numBuffers | swapInterval\n");
gralloc_dump_string(dump_strings, "---- +----- +------+-------+--------+------+------------+------------+\n");
gralloc_dump_string(dump_strings, " %d | %d | %d | %3.3f | %3.3f | %3.3f| %d | %d |\n",
id, m->vinfo[id].xres, m->vinfo[id].yres,
m->xdpi[id], m->ydpi[id],
m->fps[id], m->numBuffers[id], m->swapInterval[id]);
gralloc_dump_string(dump_strings,
"--------------------------dump Gralloc framebuffer info end :-------------------------\n");
pthread_mutex_unlock(&g_frambuffer_dump_lock);
ALOGD("%s", dump_strings.string());
}
void gralloc_debug_update_config(void)
{
char property[PROPERTY_VALUE_MAX];
property_get(GRALLOC_PROPERTY_DEBUG_DUMP, property, "false");
if (strcmp(property, "true") == 0) {
g_debug_dump_enable = true;
} else {
g_debug_dump_enable = false;
}
property_get(GRALLOC_PROPERTY_DEBUG_CAPTURE, property, "false");
if (strcmp(property, "true") == 0) {
g_debug_capture_enable = true;
} else {
g_debug_capture_enable = false;
}
}
bool gralloc_debug_dump_is_enabled(void)
{
return g_debug_dump_enable;
}
bool gralloc_debug_capture_is_enabled(void)
{
return g_debug_capture_enable;
}