g2d_fill_dmabuf.c
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <sys/types.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/mman.h>
#include <string.h>
#include <signal.h>
#include <signal.h>
#include <time.h>
#include <linux/fb.h>
#include <linux/kernel.h>
#include <sys/ioctl.h>
#include <errno.h>
#include "include/g2d_driver_enh.h"
#include "include/ion_head.h"
struct test_info_t
{
g2d_fillrect_h info;
int fd;
int ion_fd;
char filename[64];
char out_filename[64];
FILE *fp;
struct ion_info dst_ion;
};
struct test_info_t test_info;
/* Signal handler */
static void terminate(int sig_no)
{
int val[6];
memset(val,0,sizeof(val));
printf("Got signal %d, exiting ...\n", sig_no);
if(test_info.fd == -1)
{
printf("EXIT:");
exit(1);
}
close(test_info.fd);
printf("EXIT:");
exit(1);
}
int parse_cmdline(int argc, char **argv, struct test_info_t *p)
{
int err = 0;
int i = 0;
while(i<argc) {
printf("%s ",argv[i]);
i++;
}
printf("\n");
i = 0;
while(i < argc) {
if ( ! strcmp(argv[i], "-out_fb")) {
if (argc > i+4) {
i++;
p->info.dst_image_h.format = atoi(argv[i]);
i++;
p->info.dst_image_h.width = atoi(argv[i]);
i++;
p->info.dst_image_h.height = atoi(argv[i]);
} else {
printf("-out_fb para err!\n\n");
err ++;
}
}
if ( ! strcmp(argv[i], "-dst_rect")) {
if (argc > i+4) {
i++;
p->info.dst_image_h.clip_rect.x = atoi(argv[i]);
i++;
p->info.dst_image_h.clip_rect.y = atoi(argv[i]);
i++;
p->info.dst_image_h.clip_rect.w = atoi(argv[i]);
i++;
p->info.dst_image_h.clip_rect.h = atoi(argv[i]);
} else {
printf("-out_fb para err!\n\n");
err ++;
}
}
if ( ! strcmp(argv[i], "-out_file")) {
if (argc > i+1) {
i++;
p->out_filename[0] = '\0';
sprintf(p->out_filename,"%s",argv[i]);
printf("out_file=%s\n", argv[i]);
} else {
printf("no file described!!\n");
err ++;
}
}
if ( ! strcmp(argv[i], "-color")) {
if (argc > i+1) {
i+=1;
p->info.dst_image_h.color = atoll(argv[i]);
}
}
if ( ! strcmp(argv[i], "-alpha_mode")) {
if (argc > i+1) {
i+=1;
p->info.dst_image_h.mode = atoi(argv[i]);
}
}
if ( ! strcmp(argv[i], "-alpha")) {
if (argc > i+1) {
i+=1;
p->info.dst_image_h.alpha = atoi(argv[i]);
}
}
i++;
}
if(err > 0) {
printf("example : --------\n");
return -1;
} else
return 0;
}
static void install_sig_handler(void)
{
signal(SIGBUS, terminate);
signal(SIGFPE, terminate);
signal(SIGHUP, terminate);
signal(SIGILL, terminate);
signal(SIGINT, terminate);
signal(SIGIOT, terminate);
signal(SIGPIPE, terminate);
signal(SIGQUIT, terminate);
signal(SIGSEGV, terminate);
signal(SIGSYS, terminate);
signal(SIGTERM, terminate);
signal(SIGTRAP, terminate);
signal(SIGUSR1, terminate);
signal(SIGUSR2, terminate);
}
#define DISP_MEM_REQUEST 0x2c0
#define DISP_MEM_RELEASE 0x2c1
#define DISP_MEM_GETADR 0x2c2
#define DISPALIGN(value, align) ((align==0)?(unsigned long)value:((((unsigned long)value) + ((align) - 1)) & ~((align) - 1)))
int ion_open(void)
{
int fd = open("/dev/ion", O_RDONLY | O_CLOEXEC);
if (fd < 0)
printf("open ion device failed!%s\n", strerror(errno));
printf("[%s]: success fd = %d\n", __func__, fd);
return fd;
}
/**
* @name :disp_layer_is_iommu_enabled
* @brief :judge whether iommu is enabled
* @return :1 if iommu enabled or 0 if iommu disable
*/
static int is_iommu_enabled(void)
{
struct stat iommu_sysfs;
if (stat("/sys/class/iommu", &iommu_sysfs) == 0 &&
S_ISDIR(iommu_sysfs.st_mode))
return 1;
else
return 0;
}
int ion_memory_request(struct ion_info *ion, int mem_size)
{
struct ion_allocation_data data;
int ret = -1;
int ion_fd = 0;;
if (test_info.ion_fd <= 0) {
test_info.ion_fd = ion_open();
if (test_info.ion_fd < 0) {
return -1;
}
}
ion_fd = test_info.ion_fd;
printf("%s(%d): ion_fd %d\n", __func__, __LINE__, ion_fd);
/* alloc buffer */
if (is_iommu_enabled())
{
printf("---> is_iommu_enabled \n");
data.heap_id_mask = ION_SYSTEM_HEAP_MASK;
}
else
{
printf("---> is_iommu_enabled fail\n");
data.heap_id_mask = ION_DMA_HEAP_MASK;
}
data.len = mem_size;
data.flags = ION_FLAG_CACHED;
printf("%s(%d): ION_HEAP_TYPE 0x%x\n", __func__, __LINE__, data.heap_id_mask);
ret = ioctl(ion_fd, ION_IOC_ALLOC, &data);
if(ret < 0) {
printf("%s(%d): ION_IOC_ALLOC err, ret = %d\n", __func__, __LINE__, ret);
data.fd = -1;
goto out;
}
printf("%s(%d): ION_IOC_ALLOC succes, dmabuf-fd = %d, size = %d\n",
__func__, __LINE__, ret, data.len);
printf("\n");
ion->virt_addr = mmap(NULL, mem_size, PROT_READ|PROT_WRITE, MAP_SHARED, data.fd, 0);
if (ion->virt_addr == MAP_FAILED) {
printf("%s(%d): mmap err, ret %p\n", __func__, __LINE__, ion->virt_addr);
data.fd = -1;
}
ion->alloc_data = data;
out:
return data.fd;
}
void ion_memory_release(int fd)
{
close(fd);
return;
}
int main(int argc, char **argv)
{
unsigned long arg[6];
int rv;
int i,n;
int ret;
int out_size;
int dst_fd = 0;
int fb_width, fb_height;
install_sig_handler();
memset(&test_info, 0, sizeof(struct test_info_t));
rv = parse_cmdline(argc,argv, &test_info);
if(rv < 0) {
printf("parse_command fail");
return -1;
}
if((test_info.fd = open("/dev/g2d",O_RDWR)) == -1) {
printf("open g2d device fail!\n");
close(test_info.fd);
return -1;
}
out_size = test_info.info.dst_image_h.width * test_info.info.dst_image_h.height * 4;
printf("out_size=%d\n", out_size);
printf("ready to open dst file %s \n", test_info.filename);
dst_fd = ion_memory_request(&test_info.dst_ion, out_size);
if(dst_fd <= 0)
printf("request dst_mem failed! \n");
test_info.info.dst_image_h.fd = dst_fd;
fb_width = test_info.info.dst_image_h.width;
fb_height = test_info.info.dst_image_h.height;
printf("dst:format=0x%x,color=0x%x \n img w=%d, h=%d, \n rect x=%d, y=%d, w=%d, h=%d, align=%d\n\n",
test_info.info.dst_image_h.format, test_info.info.dst_image_h.color,
test_info.info.dst_image_h.width, test_info.info.dst_image_h.height,
test_info.info.dst_image_h.clip_rect.x, test_info.info.dst_image_h.clip_rect.y,
test_info.info.dst_image_h.clip_rect.w, test_info.info.dst_image_h.clip_rect.h,
test_info.info.dst_image_h.align[0]);
sleep(1);
/* fill color */
if(ioctl(test_info.fd , G2D_CMD_FILLRECT_H ,(unsigned long)(&test_info.info)) < 0)
{
printf("[%d][%s][%s]G2D_CMD_FILLRECT_H failure!\n",__LINE__, __FILE__,__FUNCTION__);
ion_memory_release(dst_fd);
close(test_info.fd);
return -1;
}
printf("[%d][%s][%s]G2D_CMD_FILLRECT_H Successful!\n",__LINE__, __FILE__,__FUNCTION__);
/* save result data to file */
printf("save result data to file %s \n", test_info.out_filename);
/* save result data to file */
if((test_info.fp = fopen(test_info.out_filename, "wb+")) == NULL) {
printf("open file %s fail. \n", test_info.out_filename);
ion_memory_release(dst_fd);
return -1;
} else {
printf("open file %s ok. \n", test_info.out_filename);
}
printf("==out_size=%d, addr=%p==\n", out_size, test_info.dst_ion.virt_addr);
ret = fwrite(test_info.dst_ion.virt_addr, out_size, 1, test_info.fp);
printf("fwrite,ret=%d\n", ret);
munmap(test_info.dst_ion.virt_addr, out_size);
fclose(test_info.fp);
ion_memory_release(dst_fd);
close(test_info.fd);
return 0;
}
编译指令:
STAGING_DIR="" /opt/T113_Tina5.0/prebuilt/rootfsbuilt/arm/toolchain-sunxi-glibc-gcc-830/toolchain/bin/arm-openwrt-linux-gcc -o g2d_fill_dmabuf src/g2d_fill_dmabuf.c
运行指令:
chmod +x /tmp/g2d_fill_dmabuf && /tmp/g2d_fill_dmabuf -out_fb 2 1920 1200 -dst_rect 0 0 1920 1200 -out_file /tmp/fill_dmabuf_0_1920x1200_abgr8888_2.bin -color 570460160 -alpha_mode 2 -alpha 128
运行日志:
#chmod +x /tmp/g2d_fill_dmabuf && /tmp/g2d_fill_dmabuf -out_fb 2 1920 1
200 -dst_rect 0 0 1920 1200 -out_file /tmp/fill_dmabuf_0_1920x1200_abgr8888_2.bi
n -color 570460160 -alpha_mode 2 -alpha 128
/tmp/g2d_fill_dmabuf -out_fb 2 1920 1200 -dst_rect 0 0 1920 1200 -out_file /tmp/fill_dmabuf_0_1920x1200_abgr8888_2.bin -color 570460160 -alpha_mode 2 -alpha 128
out_file=/tmp/fill_dmabuf_0_1920x1200_abgr8888_2.bin
out_size=9216000
ready to open dst file
[ion_open]: success fd = 4
ion_memory_request(197): ion_fd 4
---> is_iommu_enabled
ion_memory_request(214): ION_HEAP_TYPE 0x1
ion_memory_request(223): ION_IOC_ALLOC succes, dmabuf-fd = 0, size = -1097396703
dst:format=0x2,color=0x22008800
img w=1920, h=1200,
rect x=0, y=0, w=1920, h=1200, align=0
[309][g2d_fill_dmabuf.c][main]G2D_CMD_FILLRECT_H Successful!
save result data to file /tmp/fill_dmabuf_0_1920x1200_abgr8888_2.bin
open file /tmp/fill_dmabuf_0_1920x1200_abgr8888_2.bin ok.
==out_size=9216000, addr=0xb6549000==
fwrite,ret=1
离线
连续测试10000次 1920*1200 填充:
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <sys/types.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/mman.h>
#include <string.h>
#include <signal.h>
#include <signal.h>
#include <time.h>
#include <linux/fb.h>
#include <linux/kernel.h>
#include <sys/ioctl.h>
#include <errno.h>
#include "include/g2d_driver_enh.h"
#include "include/ion_head.h"
struct test_info_t
{
g2d_fillrect_h info;
int fd;
int ion_fd;
char filename[64];
char out_filename[64];
FILE *fp;
struct ion_info dst_ion;
};
struct test_info_t test_info;
/* Signal handler */
static void terminate(int sig_no)
{
int val[6];
memset(val,0,sizeof(val));
printf("Got signal %d, exiting ...\n", sig_no);
if(test_info.fd == -1)
{
printf("EXIT:");
exit(1);
}
close(test_info.fd);
printf("EXIT:");
exit(1);
}
int parse_cmdline(int argc, char **argv, struct test_info_t *p)
{
int err = 0;
int i = 0;
while(i<argc) {
printf("%s ",argv[i]);
i++;
}
printf("\n");
i = 0;
while(i < argc) {
if ( ! strcmp(argv[i], "-out_fb")) {
if (argc > i+4) {
i++;
p->info.dst_image_h.format = atoi(argv[i]);
i++;
p->info.dst_image_h.width = atoi(argv[i]);
i++;
p->info.dst_image_h.height = atoi(argv[i]);
} else {
printf("-out_fb para err!\n\n");
err ++;
}
}
if ( ! strcmp(argv[i], "-dst_rect")) {
if (argc > i+4) {
i++;
p->info.dst_image_h.clip_rect.x = atoi(argv[i]);
i++;
p->info.dst_image_h.clip_rect.y = atoi(argv[i]);
i++;
p->info.dst_image_h.clip_rect.w = atoi(argv[i]);
i++;
p->info.dst_image_h.clip_rect.h = atoi(argv[i]);
} else {
printf("-out_fb para err!\n\n");
err ++;
}
}
if ( ! strcmp(argv[i], "-out_file")) {
if (argc > i+1) {
i++;
p->out_filename[0] = '\0';
sprintf(p->out_filename,"%s",argv[i]);
printf("out_file=%s\n", argv[i]);
} else {
printf("no file described!!\n");
err ++;
}
}
if ( ! strcmp(argv[i], "-color")) {
if (argc > i+1) {
i+=1;
p->info.dst_image_h.color = atoll(argv[i]);
}
}
if ( ! strcmp(argv[i], "-alpha_mode")) {
if (argc > i+1) {
i+=1;
p->info.dst_image_h.mode = atoi(argv[i]);
}
}
if ( ! strcmp(argv[i], "-alpha")) {
if (argc > i+1) {
i+=1;
p->info.dst_image_h.alpha = atoi(argv[i]);
}
}
i++;
}
if(err > 0) {
printf("example : --------\n");
return -1;
} else
return 0;
}
static void install_sig_handler(void)
{
signal(SIGBUS, terminate);
signal(SIGFPE, terminate);
signal(SIGHUP, terminate);
signal(SIGILL, terminate);
signal(SIGINT, terminate);
signal(SIGIOT, terminate);
signal(SIGPIPE, terminate);
signal(SIGQUIT, terminate);
signal(SIGSEGV, terminate);
signal(SIGSYS, terminate);
signal(SIGTERM, terminate);
signal(SIGTRAP, terminate);
signal(SIGUSR1, terminate);
signal(SIGUSR2, terminate);
}
#define DISP_MEM_REQUEST 0x2c0
#define DISP_MEM_RELEASE 0x2c1
#define DISP_MEM_GETADR 0x2c2
#define DISPALIGN(value, align) ((align==0)?(unsigned long)value:((((unsigned long)value) + ((align) - 1)) & ~((align) - 1)))
int ion_open(void)
{
int fd = open("/dev/ion", O_RDONLY | O_CLOEXEC);
if (fd < 0)
printf("open ion device failed!%s\n", strerror(errno));
printf("[%s]: success fd = %d\n", __func__, fd);
return fd;
}
/**
* @name :disp_layer_is_iommu_enabled
* @brief :judge whether iommu is enabled
* @return :1 if iommu enabled or 0 if iommu disable
*/
static int is_iommu_enabled(void)
{
struct stat iommu_sysfs;
if (stat("/sys/class/iommu", &iommu_sysfs) == 0 &&
S_ISDIR(iommu_sysfs.st_mode))
return 1;
else
return 0;
}
int ion_memory_request(struct ion_info *ion, int mem_size)
{
struct ion_allocation_data data;
int ret = -1;
int ion_fd = 0;;
if (test_info.ion_fd <= 0) {
test_info.ion_fd = ion_open();
if (test_info.ion_fd < 0) {
return -1;
}
}
ion_fd = test_info.ion_fd;
printf("%s(%d): ion_fd %d\n", __func__, __LINE__, ion_fd);
/* alloc buffer */
if (is_iommu_enabled())
{
printf("---> is_iommu_enabled \n");
data.heap_id_mask = ION_SYSTEM_HEAP_MASK;
}
else
{
printf("---> is_iommu_enabled fail\n");
data.heap_id_mask = ION_DMA_HEAP_MASK;
}
data.len = mem_size;
data.flags = ION_FLAG_CACHED;
printf("%s(%d): ION_HEAP_TYPE 0x%x\n", __func__, __LINE__, data.heap_id_mask);
ret = ioctl(ion_fd, ION_IOC_ALLOC, &data);
if(ret < 0) {
printf("%s(%d): ION_IOC_ALLOC err, ret = %d\n", __func__, __LINE__, ret);
data.fd = -1;
goto out;
}
printf("%s(%d): ION_IOC_ALLOC succes, dmabuf-fd = %d, size = %d\n",
__func__, __LINE__, ret, data.len);
printf("\n");
ion->virt_addr = mmap(NULL, mem_size, PROT_READ|PROT_WRITE, MAP_SHARED, data.fd, 0);
if (ion->virt_addr == MAP_FAILED) {
printf("%s(%d): mmap err, ret %p\n", __func__, __LINE__, ion->virt_addr);
data.fd = -1;
}
ion->alloc_data = data;
out:
return data.fd;
}
void ion_memory_release(int fd)
{
close(fd);
return;
}
int main(int argc, char **argv)
{
unsigned long arg[6];
int rv;
int i,n;
int ret;
int out_size;
int dst_fd = 0;
int fb_width, fb_height;
install_sig_handler();
memset(&test_info, 0, sizeof(struct test_info_t));
rv = parse_cmdline(argc,argv, &test_info);
if(rv < 0) {
printf("parse_command fail");
return -1;
}
if((test_info.fd = open("/dev/g2d",O_RDWR)) == -1) {
printf("open g2d device fail!\n");
close(test_info.fd);
return -1;
}
out_size = test_info.info.dst_image_h.width * test_info.info.dst_image_h.height * 4;
printf("out_size=%d\n", out_size);
printf("ready to open dst file %s \n", test_info.filename);
dst_fd = ion_memory_request(&test_info.dst_ion, out_size);
if(dst_fd <= 0)
printf("request dst_mem failed! \n");
test_info.info.dst_image_h.fd = dst_fd;
fb_width = test_info.info.dst_image_h.width;
fb_height = test_info.info.dst_image_h.height;
printf("dst:format=0x%x,color=0x%x \n img w=%d, h=%d, \n rect x=%d, y=%d, w=%d, h=%d, align=%d\n\n",
test_info.info.dst_image_h.format, test_info.info.dst_image_h.color,
test_info.info.dst_image_h.width, test_info.info.dst_image_h.height,
test_info.info.dst_image_h.clip_rect.x, test_info.info.dst_image_h.clip_rect.y,
test_info.info.dst_image_h.clip_rect.w, test_info.info.dst_image_h.clip_rect.h,
test_info.info.dst_image_h.align[0]);
sleep(1);
while(1) {
static int i = 0;
if(i > 10000) break;
/* fill color */
if(ioctl(test_info.fd , G2D_CMD_FILLRECT_H ,(unsigned long)(&test_info.info)) < 0)
{
printf("[%d][%s][%s]G2D_CMD_FILLRECT_H failure!\n",__LINE__, __FILE__,__FUNCTION__);
ion_memory_release(dst_fd);
close(test_info.fd);
return -1;
}
i++;
}
printf("[%d][%s][%s]G2D_CMD_FILLRECT_H Successful!\n",__LINE__, __FILE__,__FUNCTION__);
/* save result data to file */
printf("save result data to file %s \n", test_info.out_filename);
/* save result data to file */
if((test_info.fp = fopen(test_info.out_filename, "wb+")) == NULL) {
printf("open file %s fail. \n", test_info.out_filename);
ion_memory_release(dst_fd);
return -1;
} else {
printf("open file %s ok. \n", test_info.out_filename);
}
printf("==out_size=%d, addr=%p==\n", out_size, test_info.dst_ion.virt_addr);
ret = fwrite(test_info.dst_ion.virt_addr, out_size, 1, test_info.fp);
printf("fwrite,ret=%d\n", ret);
munmap(test_info.dst_ion.virt_addr, out_size);
fclose(test_info.fp);
ion_memory_release(dst_fd);
close(test_info.fd);
return 0;
}
chmod +x /tmp/g2d_fill_dmabuf && /tmp/g2d_fill_dmabuf -out_fb 2 1920 1200 -dst_rect 0 0 1920 1200 -out_file tmp/fill_dmabuf_0_1920x1200_abgr8888_2.bin -color 570460160 -alpha_mode 2 -alpha 128
# date && chmod +x /tmp/g2d_fill_dmabuf && /tmp/g2d_fill_dmabuf -out_fb 2 1920 1
200 -dst_rect 0 0 1920 1200 -out_file /tmp/fill_dmabuf_0_1920x1200_abgr8888_2.bi
n -color 570460160 -alpha_mode 2 -alpha 128 && date
Sat Jun 29 20:59:03 CST 2024
/tmp/g2d_fill_dmabuf -out_fb 2 1920 1200 -dst_rect 0 0 1920 1200 -out_file /tmp/fill_dmabuf_0_1920x1200_abgr8888_2.bin -color 570460160 -alpha_mode 2 -alpha 128
out_file=/tmp/fill_dmabuf_0_1920x1200_abgr8888_2.bin
out_size=9216000
ready to open dst file
[ion_open]: success fd = 4
ion_memory_request(197): ion_fd 4
---> is_iommu_enabled
ion_memory_request(214): ION_HEAP_TYPE 0x1
ion_memory_request(223): ION_IOC_ALLOC succes, dmabuf-fd = 0, size = -1097396703
dst:format=0x2,color=0x22008800
img w=1920, h=1200,
rect x=0, y=0, w=1920, h=1200, align=0
[309][g2d_fill_dmabuf.c][main]G2D_CMD_FILLRECT_H Successful!
save result data to file /tmp/fill_dmabuf_0_1920x1200_abgr8888_2.bin
open file /tmp/fill_dmabuf_0_1920x1200_abgr8888_2.bin ok.
==out_size=9216000, addr=0xb6549000==
fwrite,ret=1
Sat Jun 29 21:01:19 CST 2024
处理速度 73fps
# echo $((10000/(120+16)))
73
#
离线
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <sys/types.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/mman.h>
#include <string.h>
#include <signal.h>
#include <signal.h>
#include <time.h>
#include <linux/fb.h>
#include <linux/kernel.h>
#include <sys/ioctl.h>
#include <errno.h>
#include "include/g2d_driver_enh.h"
#include "include/ion_head.h"
struct test_info_t
{
g2d_fillrect_h info;
int fd;
int ion_fd;
char filename[64];
char out_filename[64];
FILE *fp;
struct ion_info dst_ion;
};
struct test_info_t test_info;
/* Signal handler */
static void terminate(int sig_no)
{
int val[6];
memset(val,0,sizeof(val));
printf("Got signal %d, exiting ...\n", sig_no);
if(test_info.fd == -1)
{
printf("EXIT:");
exit(1);
}
close(test_info.fd);
printf("EXIT:");
exit(1);
}
static void install_sig_handler(void)
{
signal(SIGBUS, terminate);
signal(SIGFPE, terminate);
signal(SIGHUP, terminate);
signal(SIGILL, terminate);
signal(SIGINT, terminate);
signal(SIGIOT, terminate);
signal(SIGPIPE, terminate);
signal(SIGQUIT, terminate);
signal(SIGSEGV, terminate);
signal(SIGSYS, terminate);
signal(SIGTERM, terminate);
signal(SIGTRAP, terminate);
signal(SIGUSR1, terminate);
signal(SIGUSR2, terminate);
}
int ion_open(void)
{
int fd = open("/dev/ion", O_RDONLY | O_CLOEXEC);
if (fd < 0)
printf("open ion device failed!%s\n", strerror(errno));
printf("[%s]: success fd = %d\n", __func__, fd);
return fd;
}
/**
* @name :disp_layer_is_iommu_enabled
* @brief :judge whether iommu is enabled
* @return :1 if iommu enabled or 0 if iommu disable
*/
static int is_iommu_enabled(void)
{
struct stat iommu_sysfs;
if (stat("/sys/class/iommu", &iommu_sysfs) == 0 &&
S_ISDIR(iommu_sysfs.st_mode))
return 1;
else
return 0;
}
int ion_memory_request(struct ion_info *ion, int mem_size)
{
struct ion_allocation_data data;
int ret = -1;
int ion_fd = 0;;
if (test_info.ion_fd <= 0) {
test_info.ion_fd = ion_open();
if (test_info.ion_fd < 0) {
return -1;
}
}
ion_fd = test_info.ion_fd;
printf("%s(%d): ion_fd %d\n", __func__, __LINE__, ion_fd);
/* alloc buffer */
if (is_iommu_enabled())
{
printf("---> is_iommu_enabled \n");
data.heap_id_mask = ION_SYSTEM_HEAP_MASK;
}
else
{
printf("---> is_iommu_enabled fail\n");
data.heap_id_mask = ION_DMA_HEAP_MASK;
}
data.len = mem_size;
data.flags = ION_FLAG_CACHED;
printf("%s(%d): ION_HEAP_TYPE 0x%x\n", __func__, __LINE__, data.heap_id_mask);
ret = ioctl(ion_fd, ION_IOC_ALLOC, &data);
if(ret < 0) {
printf("%s(%d): ION_IOC_ALLOC err, ret = %d\n", __func__, __LINE__, ret);
data.fd = -1;
goto out;
}
printf("%s(%d): ION_IOC_ALLOC succes, dmabuf-fd = %d, size = %d\n",
__func__, __LINE__, ret, data.len);
printf("\n");
ion->virt_addr = mmap(NULL, mem_size, PROT_READ|PROT_WRITE, MAP_SHARED, data.fd, 0);
if (ion->virt_addr == MAP_FAILED) {
printf("%s(%d): mmap err, ret %p\n", __func__, __LINE__, ion->virt_addr);
data.fd = -1;
}
ion->alloc_data = data;
out:
return data.fd;
}
void ion_memory_release(int fd)
{
close(fd);
return;
}
int main(int argc, char **argv)
{
unsigned long arg[6];
int rv;
int i,n;
int ret;
int out_size;
int dst_fd = 0;
int fb_width, fb_height;
install_sig_handler();
memset(&test_info, 0, sizeof(struct test_info_t));
if((test_info.fd = open("/dev/g2d",O_RDWR)) == -1) {
printf("open g2d device fail!\n");
close(test_info.fd);
return -1;
}
strcpy(test_info.out_filename, "/tmp/fill_dmabuf_1920x1200_bgra8888.bin"); //pixelviewer的解析格式和g2d format刚好反过来
test_info.info.dst_image_h.width = 1920;
test_info.info.dst_image_h.height = 1200;
out_size = test_info.info.dst_image_h.width * test_info.info.dst_image_h.height * 4;
printf("out_size=%d\n", out_size);
dst_fd = ion_memory_request(&test_info.dst_ion, out_size);
if(dst_fd <= 0)
printf("request dst_mem failed! \n");
test_info.info.dst_image_h.fd = dst_fd;
fb_width = test_info.info.dst_image_h.width;
fb_height = test_info.info.dst_image_h.height;
//Red
test_info.info.dst_image_h.format = G2D_FORMAT_ARGB8888;
test_info.info.dst_image_h.width = 1920;
test_info.info.dst_image_h.height = 1200;
test_info.info.dst_image_h.clip_rect.x = 0;
test_info.info.dst_image_h.clip_rect.y = 0;
test_info.info.dst_image_h.clip_rect.w = 300;
test_info.info.dst_image_h.clip_rect.h = 1200;
test_info.info.dst_image_h.color = 0xFFFF0000; //A,R,G,B
test_info.info.dst_image_h.mode = G2D_MIXER_ALPHA; //G2D_PIXEL_ALPHA,G2D_GLOBAL_ALPHA,G2D_MIXER_ALPHA
test_info.info.dst_image_h.alpha = 0x30;
if(ioctl(test_info.fd , G2D_CMD_FILLRECT_H ,(unsigned long)(&test_info.info)) < 0)
{
printf("[%d][%s][%s]G2D_CMD_FILLRECT_H failure!\n",__LINE__, __FILE__,__FUNCTION__);
ion_memory_release(dst_fd);
close(test_info.fd);
return -1;
}
if(ioctl(test_info.fd , G2D_CMD_FILLRECT_H ,(unsigned long)(&test_info.info)) < 0)
{
printf("[%d][%s][%s]G2D_CMD_FILLRECT_H failure!\n",__LINE__, __FILE__,__FUNCTION__);
ion_memory_release(dst_fd);
close(test_info.fd);
return -1;
}
//Green
test_info.info.dst_image_h.format = G2D_FORMAT_ARGB8888;
test_info.info.dst_image_h.width = 1920;
test_info.info.dst_image_h.height = 1200;
test_info.info.dst_image_h.clip_rect.x = 400;
test_info.info.dst_image_h.clip_rect.y = 0;
test_info.info.dst_image_h.clip_rect.w = 300;
test_info.info.dst_image_h.clip_rect.h = 1200;
test_info.info.dst_image_h.color = 0xFF00FF00;//A,R,G,B
test_info.info.dst_image_h.mode = 1;
test_info.info.dst_image_h.alpha = 0xFF;
if(ioctl(test_info.fd , G2D_CMD_FILLRECT_H ,(unsigned long)(&test_info.info)) < 0)
{
printf("[%d][%s][%s]G2D_CMD_FILLRECT_H failure!\n",__LINE__, __FILE__,__FUNCTION__);
ion_memory_release(dst_fd);
close(test_info.fd);
return -1;
}
//Blue
test_info.info.dst_image_h.format = G2D_FORMAT_ARGB8888;
test_info.info.dst_image_h.width = 1920;
test_info.info.dst_image_h.height = 1200;
test_info.info.dst_image_h.clip_rect.x = 800;
test_info.info.dst_image_h.clip_rect.y = 0;
test_info.info.dst_image_h.clip_rect.w = 300;
test_info.info.dst_image_h.clip_rect.h = 1200;
test_info.info.dst_image_h.color = 0xFF0000FF;//A,R,G,B
test_info.info.dst_image_h.mode = 1;
test_info.info.dst_image_h.alpha = 0xFF;
/* fill color */
if(ioctl(test_info.fd , G2D_CMD_FILLRECT_H ,(unsigned long)(&test_info.info)) < 0)
{
printf("[%d][%s][%s]G2D_CMD_FILLRECT_H failure!\n",__LINE__, __FILE__,__FUNCTION__);
ion_memory_release(dst_fd);
close(test_info.fd);
return -1;
}
/* save result data to file */
printf("save result data to file %s \n", test_info.out_filename);
/* save result data to file */
if((test_info.fp = fopen(test_info.out_filename, "wb+")) == NULL) {
printf("open file %s fail. \n", test_info.out_filename);
ion_memory_release(dst_fd);
return -1;
} else {
printf("open file %s ok. \n", test_info.out_filename);
}
printf("==out_size=%d, addr=%p==\n", out_size, test_info.dst_ion.virt_addr);
ret = fwrite(test_info.dst_ion.virt_addr, out_size, 1, test_info.fp);
printf("fwrite,ret=%d\n", ret);
munmap(test_info.dst_ion.virt_addr, out_size);
fclose(test_info.fp);
ion_memory_release(dst_fd);
close(test_info.fd);
return 0;
}
STAGING_DIR="" /opt/T113_Tina5.0/prebuilt/rootfsbuilt/arm/toolchain-sunxi-glibc-gcc-830/toolchain/bin/arm-openwrt-linux-gcc -o /mnt/hgfs/D/g2d_fill_dmabuf src/g2d_fill_dmabuf.c
# chmod +x /tmp/g2d_fill_dmabuf && /tmp/g2d_fill_dmabuf
out_size=9216000
[ion_open]: success fd = 4
ion_memory_request(107): ion_fd 4
---> is_iommu_enabled
ion_memory_request(124): ION_HEAP_TYPE 0x1
ion_memory_request(133): ION_IOC_ALLOC succes, dmabuf-fd = 0, size = 9216000
save result data to file /tmp/fill_dmabuf_1920x1200_bgra8888.bin
open file /tmp/fill_dmabuf_1920x1200_bgra8888.bin ok.
==out_size=9216000, addr=0xb6500000==
fwrite,ret=1
#
#
adb pull /tmp/fill_dmabuf_1920x1200_bgra8888.bin
离线
旋转测试:
chmod +x /tmp/g2d_lbc_rot && /tmp/g2d_lbc_rot -flag 256 -in_fb 0 800 480 -src_rect 0 0 800 480 -out_fb 0 480 800 -dst_rect 0 0 480 800 -src_file /tmp/src_800x480_rgb.bin -dst_file /tmp/en_src_480x800_bgra888_rotate_90.bin
原图:
旋转90°:
离线
测试水平镜像:
chmod +x /tmp/g2d_lbc_rot && /tmp/g2d_lbc_rot -flag 4096 -in_fb 0 800 480 -src_rect 0 0 800 480 -out_fb 0 800 480 -dst_rect 0 0 800 480 -src_file /tmp/src_800x480_rgb.bin -dst_file /tmp/en_dst_800x480_bgra888_flip_h.bin
离线
但是开启lbc失败:
chmod +x /tmp/g2d_lbc_rot && /tmp/g2d_lbc_rot -flag 4096 -in_fb 0 800 480 -src_rect 0 0 800 480 -out_fb 0 800 480 -dst_rect 0 0 800 480 -src_file /tmp/src_800x480_rgb.bin -dst_file /tmp/en_dst_800x480_bgra888_flip_h.bin -lbc 1 -cmp_ratio 400 -enc_lossy 1 -dec_lossy 1
# chmod +x /tmp/g2d_lbc_rot && /tmp/g2d_lbc_rot -flag 4096 -in_fb 0 800 480 -src
_rect 0 0 800 480 -out_fb 0 800 480 -dst_rect 0 0 800 480 -src_file /tmp/src_800
x480_rgb.bin -dst_file /tmp/en_dst_800x480_bgra888_flip_h.bin -lbc 1 -cmp_ratio
400 -enc_lossy 1 -dec_lossy 1
/tmp/g2d_lbc_rot -flag 4096 -in_fb 0 800 480 -src_rect 0 0 800 480 -out_fb 0 800 480 -dst_rect 0 0 800 480 -src_file /tmp/src_800x480_rgb.bin -dst_file /tmp/en_dst_800x480_bgra888_flip_h.bin -lbc 1 -cmp_ratio 400 -enc_lossy 1 -dec_lossy 1
src_file=/tmp/src_800x480_rgb.bin
dst_file=/tmp/en_dst_800x480_bgra888_flip_h.bin
in_size:1536000, out_size=1536000
ready to open src file /tmp/src_800x480_rgb.bin
[ion_open]: success fd = 4
ion_memory_request(295): ion_fd 4
ion_memory_request(306): ION_HEAP_TYPE 0x1
ion_memory_request(315): ION_IOC_ALLOC succes, dmabuf-fd = 0, size = 1536000
+++src_fd = 5
open file /tmp/src_800x480_rgb.bin ok.
read file /tmp/src_800x480_rgb.bin ,ret = 1
ready to open dst file /tmp/en_dst_800x480_bgra888_flip_h.bin
ion_memory_request(295): ion_fd 4
ion_memory_request(306): ION_HEAP_TYPE 0x1
ion_memory_request(315): ION_IOC_ALLOC succes, dmabuf-fd = 0, size = 1536000
+++dst_fd = 7
open file /tmp/en_dst_800x480_bgra888_flip_h.bin ok.
src:format=0x0, w=800, h=480, x=0, y=0, image_w=800, image_h=480, align=0
dst:format=0x0, img w=800, h=480, rect x=0, y=0, w=800, h=480, align=0
[G2D] LBC=1
[460][src/g2d_lbc_rot.c][main]G2D_CMD_LBC_ROT failure!
#
#
#
#
离线