GNU Linux-libre 4.19.268-gnu1
[releases.git] / tools / testing / selftests / android / ion / ionmap_test.c
1 #include <errno.h>
2 #include <fcntl.h>
3 #include <stdio.h>
4 #include <stdint.h>
5 #include <string.h>
6 #include <unistd.h>
7
8 #include <sys/ioctl.h>
9 #include <sys/types.h>
10 #include <sys/stat.h>
11
12 #include <linux/dma-buf.h>
13
14 #include <drm/drm.h>
15
16 #include "ion.h"
17 #include "ionutils.h"
18
19 int check_vgem(int fd)
20 {
21         drm_version_t version = { 0 };
22         char name[5];
23         int ret;
24
25         version.name_len = 4;
26         version.name = name;
27
28         ret = ioctl(fd, DRM_IOCTL_VERSION, &version);
29         if (ret)
30                 return 1;
31
32         return strcmp(name, "vgem");
33 }
34
35 int open_vgem(void)
36 {
37         int i, fd;
38         const char *drmstr = "/dev/dri/card";
39
40         fd = -1;
41         for (i = 0; i < 16; i++) {
42                 char name[80];
43
44                 sprintf(name, "%s%u", drmstr, i);
45
46                 fd = open(name, O_RDWR);
47                 if (fd < 0)
48                         continue;
49
50                 if (check_vgem(fd)) {
51                         close(fd);
52                         continue;
53                 } else {
54                         break;
55                 }
56
57         }
58         return fd;
59 }
60
61 int import_vgem_fd(int vgem_fd, int dma_buf_fd, uint32_t *handle)
62 {
63         struct drm_prime_handle import_handle = { 0 };
64         int ret;
65
66         import_handle.fd = dma_buf_fd;
67         import_handle.flags = 0;
68         import_handle.handle = 0;
69
70         ret = ioctl(vgem_fd, DRM_IOCTL_PRIME_FD_TO_HANDLE, &import_handle);
71         if (ret == 0)
72                 *handle = import_handle.handle;
73         return ret;
74 }
75
76 void close_handle(int vgem_fd, uint32_t handle)
77 {
78         struct drm_gem_close close = { 0 };
79
80         close.handle = handle;
81         ioctl(vgem_fd, DRM_IOCTL_GEM_CLOSE, &close);
82 }
83
84 int main()
85 {
86         int ret, vgem_fd;
87         struct ion_buffer_info info;
88         uint32_t handle = 0;
89         struct dma_buf_sync sync = { 0 };
90
91         info.heap_type = ION_HEAP_TYPE_SYSTEM;
92         info.heap_size = 4096;
93         info.flag_type = ION_FLAG_CACHED;
94
95         ret = ion_export_buffer_fd(&info);
96         if (ret < 0) {
97                 printf("ion buffer alloc failed\n");
98                 return -1;
99         }
100
101         vgem_fd = open_vgem();
102         if (vgem_fd < 0) {
103                 ret = vgem_fd;
104                 printf("Failed to open vgem\n");
105                 goto out_ion;
106         }
107
108         ret = import_vgem_fd(vgem_fd, info.buffd, &handle);
109
110         if (ret < 0) {
111                 printf("Failed to import buffer\n");
112                 goto out_vgem;
113         }
114
115         sync.flags = DMA_BUF_SYNC_START | DMA_BUF_SYNC_RW;
116         ret = ioctl(info.buffd, DMA_BUF_IOCTL_SYNC, &sync);
117         if (ret)
118                 printf("sync start failed %d\n", errno);
119
120         memset(info.buffer, 0xff, 4096);
121
122         sync.flags = DMA_BUF_SYNC_END | DMA_BUF_SYNC_RW;
123         ret = ioctl(info.buffd, DMA_BUF_IOCTL_SYNC, &sync);
124         if (ret)
125                 printf("sync end failed %d\n", errno);
126
127         close_handle(vgem_fd, handle);
128         ret = 0;
129
130 out_vgem:
131         close(vgem_fd);
132 out_ion:
133         ion_close_buffer_fd(&info);
134         printf("done.\n");
135         return ret;
136 }