summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorbohu2017-03-02 01:31:14 -0600
committerbohu2017-03-28 11:27:43 -0500
commita19abf17697863c2458d7d085a225ff4f3c75f75 (patch)
tree6bef3519c2d8b6e0205bb1dbc91e2f6c35cfbd42 /qemu_pipe
parent7b60bd95dfa07e86325b432465fb0043648f6c97 (diff)
downloadplatform-system-core-a19abf17697863c2458d7d085a225ff4f3c75f75.tar.gz
platform-system-core-a19abf17697863c2458d7d085a225ff4f3c75f75.tar.xz
platform-system-core-a19abf17697863c2458d7d085a225ff4f3c75f75.zip
Qemu: make the qemu_pipe_open back compatible
Commit c7b098ceb528afc62b1545377201e45f5d37f974 has changed the qemu_pipe_open interface to require the "pipe:" prefix in the service name. However in APIs 24 and before, the "pipe:" prefix is not required This causes quite some confusion and bugs since it is very common to forget the difference when working across differnet APIs. This CL is meant to make qemu_pipe_open work in both cases by doing the following: 1. try the service name as is; 2. if it fails, add 'pipe:' prefix and try the service name again. Change-Id: If9782396c03780fad1aadeb8374eb308517dc963 (cherry picked from aosp f7d64fd8e1703c54ff01c2e53b0af850977777a0)
Diffstat (limited to 'qemu_pipe')
-rw-r--r--qemu_pipe/include/qemu_pipe.h6
-rw-r--r--qemu_pipe/qemu_pipe.cpp51
2 files changed, 20 insertions, 37 deletions
diff --git a/qemu_pipe/include/qemu_pipe.h b/qemu_pipe/include/qemu_pipe.h
index 16486c087..098749899 100644
--- a/qemu_pipe/include/qemu_pipe.h
+++ b/qemu_pipe/include/qemu_pipe.h
@@ -28,8 +28,10 @@ extern "C" {
28// This file descriptor can be used as a standard pipe/socket descriptor. 28// This file descriptor can be used as a standard pipe/socket descriptor.
29// 29//
30// 'pipeName' is the name of the emulator service you want to connect to, 30// 'pipeName' is the name of the emulator service you want to connect to,
31// and must begin with 'pipe:' (e.g. 'pipe:camera' or 'pipe:opengles'). 31// and should begin with 'pipe:' (e.g. 'pipe:camera' or 'pipe:opengles').
32// 32// For backward compatibility, the 'pipe:' prefix can be omitted, and in
33// that case, qemu_pipe_open will add it for you.
34
33// On success, return a valid file descriptor, or -1/errno on failure. E.g.: 35// On success, return a valid file descriptor, or -1/errno on failure. E.g.:
34// 36//
35// EINVAL -> unknown/unsupported pipeName 37// EINVAL -> unknown/unsupported pipeName
diff --git a/qemu_pipe/qemu_pipe.cpp b/qemu_pipe/qemu_pipe.cpp
index ca3b79578..beeccb07f 100644
--- a/qemu_pipe/qemu_pipe.cpp
+++ b/qemu_pipe/qemu_pipe.cpp
@@ -34,29 +34,9 @@ using android::base::WriteFully;
34# define QEMU_PIPE_DEBUG(...) (void)0 34# define QEMU_PIPE_DEBUG(...) (void)0
35#endif 35#endif
36 36
37// Try to open a new Qemu fast-pipe. This function returns a file descriptor
38// that can be used to communicate with a named service managed by the
39// emulator.
40//
41// This file descriptor can be used as a standard pipe/socket descriptor.
42//
43// 'pipeName' is the name of the emulator service you want to connect to,
44// and must begin with 'pipe:' (e.g. 'pipe:camera' or 'pipe:opengles').
45//
46// On success, return a valid file descriptor, or -1/errno on failure. E.g.:
47//
48// EINVAL -> unknown/unsupported pipeName
49// ENOSYS -> fast pipes not available in this system.
50//
51// ENOSYS should never happen, except if you're trying to run within a
52// misconfigured emulator.
53//
54// You should be able to open several pipes to the same pipe service,
55// except for a few special cases (e.g. GSM modem), where EBUSY will be
56// returned if more than one client tries to connect to it.
57int qemu_pipe_open(const char* pipeName) { 37int qemu_pipe_open(const char* pipeName) {
58 // Sanity check. 38 // Sanity check.
59 if (!pipeName || memcmp(pipeName, "pipe:", 5) != 0) { 39 if (!pipeName) {
60 errno = EINVAL; 40 errno = EINVAL;
61 return -1; 41 return -1;
62 } 42 }
@@ -70,18 +50,24 @@ int qemu_pipe_open(const char* pipeName) {
70 50
71 // Write the pipe name, *including* the trailing zero which is necessary. 51 // Write the pipe name, *including* the trailing zero which is necessary.
72 size_t pipeNameLen = strlen(pipeName); 52 size_t pipeNameLen = strlen(pipeName);
73 if (!WriteFully(fd, pipeName, pipeNameLen + 1U)) { 53 if (WriteFully(fd, pipeName, pipeNameLen + 1U)) {
74 QEMU_PIPE_DEBUG("%s: Could not connect to %s pipe service: %s", 54 return fd;
75 __FUNCTION__, pipeName, strerror(errno)); 55 }
76 close(fd); 56
77 return -1; 57 // now, add 'pipe:' prefix and try again
58 // Note: host side will wait for the trailing '\0' to start
59 // service lookup.
60 const char pipe_prefix[] = "pipe:";
61 if (WriteFully(fd, pipe_prefix, strlen(pipe_prefix)) &&
62 WriteFully(fd, pipeName, pipeNameLen + 1U)) {
63 return fd;
78 } 64 }
79 return fd; 65 QEMU_PIPE_DEBUG("%s: Could not write to %s pipe service: %s",
66 __FUNCTION__, pipeName, strerror(errno));
67 close(fd);
68 return -1;
80} 69}
81 70
82// Send a framed message |buff| of |len| bytes through the |fd| descriptor.
83// This really adds a 4-hexchar prefix describing the payload size.
84// Returns 0 on success, and -1 on error.
85int qemu_pipe_frame_send(int fd, const void* buff, size_t len) { 71int qemu_pipe_frame_send(int fd, const void* buff, size_t len) {
86 char header[5]; 72 char header[5];
87 snprintf(header, sizeof(header), "%04zx", len); 73 snprintf(header, sizeof(header), "%04zx", len);
@@ -96,11 +82,6 @@ int qemu_pipe_frame_send(int fd, const void* buff, size_t len) {
96 return 0; 82 return 0;
97} 83}
98 84
99// Read a frame message from |fd|, and store it into |buff| of |len| bytes.
100// If the framed message is larger than |len|, then this returns -1 and the
101// content is lost. Otherwise, this returns the size of the message. NOTE:
102// empty messages are possible in a framed wire protocol and do not mean
103// end-of-stream.
104int qemu_pipe_frame_recv(int fd, void* buff, size_t len) { 85int qemu_pipe_frame_recv(int fd, void* buff, size_t len) {
105 char header[5]; 86 char header[5];
106 if (!ReadFully(fd, header, 4)) { 87 if (!ReadFully(fd, header, 4)) {