1 /* 2 * ionapp_export.c 3 * 4 * It is a user space utility to create and export android 5 * ion memory buffer fd to another process using unix domain socket as IPC. 6 * This acts like a server for ionapp_import(client). 7 * So, this server has to be started first before the client. 8 * 9 * Copyright (C) 2017 Pintu Kumar <pintu.ping (at) gmail.com> 10 * 11 * This software is licensed under the terms of the GNU General Public 12 * License version 2, as published by the Free Software Foundation, and 13 * may be copied, distributed, and modified under those terms. 14 * 15 * This program is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU General Public License for more details. 19 * 20 */ 21 22 #include <stdio.h> 23 #include <stdlib.h> 24 #include <string.h> 25 #include <unistd.h> 26 #include <errno.h> 27 #include <sys/time.h> 28 #include "ionutils.h" 29 #include "ipcsocket.h" 30 31 32 void print_usage(int argc, char *argv[]) 33 { 34 printf("Usage: %s [-h <help>] [-i <heap id>] [-s <size in bytes>]\n", 35 argv[0]); 36 } 37 38 int main(int argc, char *argv[]) 39 { 40 int opt, ret, status, heapid; 41 int sockfd, client_fd, shared_fd; 42 unsigned char *map_buf; 43 unsigned long map_len, heap_type, heap_size, flags; 44 struct ion_buffer_info info; 45 struct socket_info skinfo; 46 47 if (argc < 2) { 48 print_usage(argc, argv); 49 return -1; 50 } 51 52 heap_size = 0; 53 flags = 0; 54 55 while ((opt = getopt(argc, argv, "hi:s:")) != -1) { 56 switch (opt) { 57 case 'h': 58 print_usage(argc, argv); 59 exit(0); 60 break; 61 case 'i': 62 heapid = atoi(optarg); 63 switch (heapid) { 64 case 0: 65 heap_type = ION_HEAP_TYPE_SYSTEM; 66 break; 67 case 1: 68 heap_type = ION_HEAP_TYPE_SYSTEM_CONTIG; 69 break; 70 default: 71 printf("ERROR: heap type not supported\n"); 72 exit(1); 73 } 74 break; 75 case 's': 76 heap_size = atoi(optarg); 77 break; 78 default: 79 print_usage(argc, argv); 80 exit(1); 81 break; 82 } 83 } 84 85 if (heap_size <= 0) { 86 printf("heap_size cannot be 0\n"); 87 print_usage(argc, argv); 88 exit(1); 89 } 90 91 printf("heap_type: %ld, heap_size: %ld\n", heap_type, heap_size); 92 info.heap_type = heap_type; 93 info.heap_size = heap_size; 94 info.flag_type = flags; 95 96 /* This is server: open the socket connection first */ 97 /* Here; 1 indicates server or exporter */ 98 status = opensocket(&sockfd, SOCKET_NAME, 1); 99 if (status < 0) { 100 fprintf(stderr, "<%s>: Failed opensocket.\n", __func__); 101 goto err_socket; 102 } 103 skinfo.sockfd = sockfd; 104 105 ret = ion_export_buffer_fd(&info); 106 if (ret < 0) { 107 fprintf(stderr, "FAILED: ion_get_buffer_fd\n"); 108 goto err_export; 109 } 110 client_fd = info.ionfd; 111 shared_fd = info.buffd; 112 map_buf = info.buffer; 113 map_len = info.buflen; 114 write_buffer(map_buf, map_len); 115 116 /* share ion buf fd with other user process */ 117 printf("Sharing fd: %d, Client fd: %d\n", shared_fd, client_fd); 118 skinfo.datafd = shared_fd; 119 skinfo.buflen = map_len; 120 121 ret = socket_send_fd(&skinfo); 122 if (ret < 0) { 123 fprintf(stderr, "FAILED: socket_send_fd\n"); 124 goto err_send; 125 } 126 127 err_send: 128 err_export: 129 ion_close_buffer_fd(&info); 130 131 err_socket: 132 closesocket(sockfd, SOCKET_NAME); 133 134 return 0; 135 } 136