1 /*
2  * Copyright (C) 2016 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.android.commands.hidl_test_java;
18 
19 import static android.system.OsConstants.MAP_SHARED;
20 import static android.system.OsConstants.PROT_READ;
21 import static android.system.OsConstants.PROT_WRITE;
22 
23 import android.hardware.tests.baz.V1_0.IBase;
24 import android.hardware.tests.baz.V1_0.IBaz;
25 import android.hardware.tests.baz.V1_0.IBaz.MyHandle;
26 import android.hardware.tests.baz.V1_0.IBaz.NestedStruct;
27 import android.hardware.tests.baz.V1_0.IBazCallback;
28 import android.hardware.tests.baz.V1_0.IQuux;
29 import android.hardware.tests.memory.V2_0.IMemoryInterface;
30 import android.hardware.tests.memory.V2_0.TwoMemory;
31 import android.hardware.tests.safeunion.V1_0.ISafeUnion;
32 import android.hardware.tests.safeunion.V1_0.ISafeUnion.HandleTypeSafeUnion;
33 import android.hardware.tests.safeunion.V1_0.ISafeUnion.InterfaceTypeSafeUnion;
34 import android.hardware.tests.safeunion.V1_0.ISafeUnion.LargeSafeUnion;
35 import android.hardware.tests.safeunion.V1_0.ISafeUnion.SmallSafeUnion;
36 import android.hidl.manager.V1_0.IServiceManager;
37 import android.os.DeadObjectException;
38 import android.os.HidlMemory;
39 import android.os.HidlMemoryUtil;
40 import android.os.HidlSupport;
41 import android.os.HwBinder;
42 import android.os.HwParcel;
43 import android.os.IBinder;
44 import android.os.IHwBinder;
45 import android.os.NativeHandle;
46 import android.os.RemoteException;
47 import android.os.SharedMemory;
48 import android.system.ErrnoException;
49 import android.system.Os;
50 import android.util.Log;
51 import java.io.File;
52 import java.io.FileDescriptor;
53 import java.io.FileInputStream;
54 import java.io.FileOutputStream;
55 import java.io.IOException;
56 import java.nio.ByteBuffer;
57 import java.nio.DirectByteBuffer;
58 import java.util.ArrayList;
59 import java.util.Arrays;
60 import java.util.NoSuchElementException;
61 import java.util.Objects;
62 
63 public final class HidlTestJava {
64     private static final String TAG = "HidlTestJava";
65 
main(String[] args)66     public static void main(String[] args) {
67         int exitCode = 1;
68         try {
69             exitCode = new HidlTestJava().run(args);
70         } catch (Exception e) {
71             e.printStackTrace();
72             Log.e(TAG, "Error ", e);
73         }
74         System.exit(exitCode);
75     }
76 
run(String[] args)77     public int run(String[] args) throws RemoteException, IOException, ErrnoException {
78         HwBinder.setTrebleTestingOverride(true);
79 
80         if (args[0].equals("-c")) {
81             client();
82         } else if (args[0].equals("-s")) {
83             server();
84         } else {
85             Log.e(TAG, "Usage: HidlTestJava  -c(lient) | -s(erver)");
86             System.err.printf("Usage: HidlTestJava  -c(lient) | -s(erver)\n");
87             return 1;
88         }
89 
90         return 0;
91     }
92 
93     final class HidlDeathRecipient implements HwBinder.DeathRecipient {
94         final Object mLock = new Object();
95         boolean mCalled = false;
96         long mCookie = 0;
97 
98         @Override
serviceDied(long cookie)99         public void serviceDied(long cookie) {
100             synchronized (mLock) {
101                 mCalled = true;
102                 mCookie = cookie;
103                 mLock.notify();
104             }
105         }
106 
cookieMatches(long cookie)107         public boolean cookieMatches(long cookie) {
108             synchronized (mLock) {
109                 return mCookie == cookie;
110             }
111         }
112 
waitUntilServiceDied(long timeoutMillis)113         public boolean waitUntilServiceDied(long timeoutMillis) {
114             synchronized(mLock) {
115                 while (!mCalled) {
116                     try {
117                         mLock.wait(timeoutMillis);
118                     } catch (InterruptedException e) {
119                         continue; // Spin for another loop
120                     }
121                     break; // got notified or timeout hit
122                 }
123                 return mCalled;
124             }
125         }
126     };
127 
ExpectTrue(boolean x)128     private void ExpectTrue(boolean x) {
129         if (x) {
130             return;
131         }
132 
133         throw new RuntimeException();
134     }
135 
ExpectFalse(boolean x)136     private void ExpectFalse(boolean x) {
137         ExpectTrue(!x);
138     }
139 
ExpectWithin(double a, double b, double precision, String onError)140     private void ExpectWithin(double a, double b, double precision, String onError) {
141         if (Math.abs(a - b) < precision) {
142             return;
143         }
144         System.err.printf(
145                 "Expected '%f' to be within '%f' of '%f'. %s\n", a, precision, b, onError);
146         Log.e(TAG,
147                 "Expected '" + a + "' to be within '" + precision + "' of '" + b + "'. " + onError);
148         throw new RuntimeException();
149     }
150 
Expect(String result, String s)151     private void Expect(String result, String s) {
152         if (result.equals(s)) {
153             return;
154         }
155 
156         System.err.printf("Expected '%s', got '%s'\n", s, result);
157         Log.e(TAG, "Expected '" + s + "', got '" + result + "'");
158         throw new RuntimeException();
159     }
160 
161     // .equals and HidlSupport.interfacesEqual should have the same behavior.
ExpectEqual(android.hidl.base.V1_0.IBase l, android.hidl.base.V1_0.IBase r)162     private void ExpectEqual(android.hidl.base.V1_0.IBase l, android.hidl.base.V1_0.IBase r) {
163         ExpectTrue(Objects.equals(l, r));
164         ExpectTrue(Objects.equals(r, l));
165         ExpectTrue(HidlSupport.interfacesEqual(l, r));
166         ExpectTrue(HidlSupport.interfacesEqual(r, l));
167     }
ExpectNotEqual(android.hidl.base.V1_0.IBase l, android.hidl.base.V1_0.IBase r)168     private void ExpectNotEqual(android.hidl.base.V1_0.IBase l, android.hidl.base.V1_0.IBase r) {
169         ExpectFalse(Objects.equals(l, r));
170         ExpectFalse(Objects.equals(r, l));
171         ExpectFalse(HidlSupport.interfacesEqual(l, r));
172         ExpectFalse(HidlSupport.interfacesEqual(r, l));
173     }
174 
175     class BazCallback extends IBazCallback.Stub {
176         private boolean mCalled;
177 
BazCallback()178         public BazCallback() {
179             mCalled = false;
180         }
181 
wasCalled()182         boolean wasCalled() {
183             return mCalled;
184         }
185 
heyItsMe(IBazCallback cb)186         public void heyItsMe(IBazCallback cb) throws RemoteException {
187             mCalled = true;
188 
189             cb.heyItsMe(null);
190         }
191 
hey()192         public void hey() {
193             mCalled = true;
194         }
195 
equals(Object other)196         @Override public boolean equals(Object other) {
197             return other != null && other.getClass() == BazCallback.class &&
198                 ((BazCallback) other).mCalled == mCalled;
199         }
hashCode()200         @Override public int hashCode() { return mCalled ? 1 : 0; }
201     }
202 
numberToEnglish(int x)203     private String numberToEnglish(int x) {
204         final String[] kDigits = {
205             "zero",
206             "one",
207             "two",
208             "three",
209             "four",
210             "five",
211             "six",
212             "seven",
213             "eight",
214             "nine",
215         };
216 
217         if (x < 0) {
218             return "negative " + numberToEnglish(-x);
219         }
220 
221         if (x < 10) {
222             return kDigits[x];
223         }
224 
225         if (x <= 15) {
226             final String[] kSpecialTens = {
227                 "ten", "eleven", "twelve", "thirteen", "fourteen", "fifteen",
228             };
229 
230             return kSpecialTens[x - 10];
231         }
232 
233         if (x < 20) {
234             return kDigits[x % 10] + "teen";
235         }
236 
237         if (x < 100) {
238             final String[] kDecades = {
239                 "twenty", "thirty", "forty", "fifty", "sixty", "seventy",
240                 "eighty", "ninety",
241             };
242 
243             return kDecades[x / 10 - 2] + kDigits[x % 10];
244         }
245 
246         return "positively huge!";
247     }
248 
ExpectDeepEq(Object l, Object r)249     private void ExpectDeepEq(Object l, Object r) {
250         ExpectTrue(HidlSupport.deepEquals(l, r));
251         ExpectTrue(HidlSupport.deepHashCode(l) == HidlSupport.deepHashCode(r));
252     }
253 
ExpectDeepNe(Object l, Object r)254     private void ExpectDeepNe(Object l, Object r) {
255         ExpectTrue(!HidlSupport.deepEquals(l, r));
256     }
257 
runClientMemoryTests()258     private void runClientMemoryTests() throws RemoteException, IOException, ErrnoException {
259         IMemoryInterface memoryInterface;
260         try {
261             memoryInterface = IMemoryInterface.getService();
262         } catch (NoSuchElementException e) {
263             // If the test didn't register the memory interface, don't try to test it.
264             return;
265         }
266 
267         {
268             HidlMemory hidlMem = HidlMemoryUtil.byteArrayToHidlMemory(
269                     new byte[]{0x00, 0x12, 0x34, 0x56});
270             memoryInterface.bitwiseNot(hidlMem);
271             byte[] result = HidlMemoryUtil.hidlMemoryToByteArray(hidlMem);
272 
273             ExpectTrue(Arrays.equals(result,
274                     new byte[]{(byte) 0xFF, (byte) 0xED, (byte) 0xCB, (byte) 0xA9}));
275 
276             hidlMem.close();
277         }
278 
279         {
280             HidlMemory hidlMem = memoryInterface.getTestMem();
281             byte[] data = HidlMemoryUtil.hidlMemoryToByteArray(hidlMem);
282             for (int i = 0; i < 8; ++i) {
283                 ExpectTrue(data[i] == (byte) i);
284             }
285             hidlMem.close();
286         }
287 
288         {
289             TwoMemory in = new TwoMemory();
290             in.mem1 = HidlMemoryUtil.byteArrayToHidlMemory(new byte[]{10, 11, 12, 13});
291             in.mem2 = HidlMemoryUtil.byteArrayToHidlMemory(new byte[]{2, 4, 6, 8});
292             TwoMemory out = memoryInterface.getSumDiff(in);
293             ExpectTrue(Arrays.equals(HidlMemoryUtil.hidlMemoryToByteArray(out.mem1),
294                     new byte[]{12, 15, 18, 21}));
295             ExpectTrue(Arrays.equals(HidlMemoryUtil.hidlMemoryToByteArray(out.mem2),
296                     new byte[]{8, 7, 6, 5}));
297             in.mem1.close();
298             in.mem2.close();
299             out.mem1.close();
300             out.mem2.close();
301         }
302     }
303 
runClientSafeUnionTests()304     private void runClientSafeUnionTests() throws RemoteException, IOException {
305         ISafeUnion safeunionInterface = ISafeUnion.getService();
306 
307         {
308             // SafeUnionNoInitTest
309             LargeSafeUnion safeUnion = safeunionInterface.newLargeSafeUnion();
310             ExpectTrue(safeUnion.getDiscriminator() == LargeSafeUnion.hidl_discriminator.noinit);
311         }
312         {
313             // SafeUnionSimpleTest
314             LargeSafeUnion safeUnion = safeunionInterface.newLargeSafeUnion();
315 
316             safeUnion = safeunionInterface.setA(safeUnion, (byte) -5);
317             ExpectTrue(safeUnion.getDiscriminator() == LargeSafeUnion.hidl_discriminator.a);
318             ExpectTrue(safeUnion.a() == (byte) -5);
319 
320             safeUnion = safeunionInterface.setD(safeUnion, Long.MAX_VALUE);
321             ExpectTrue(safeUnion.getDiscriminator() == LargeSafeUnion.hidl_discriminator.d);
322             ExpectTrue(safeUnion.d() == Long.MAX_VALUE);
323         }
324         {
325             // SafeUnionArrayLikeTypesTest
326             long[] testArray = new long[] {1, -2, 3, -4, 5};
327             ArrayList<Long> testVector = new ArrayList<Long>(Arrays.asList(Long.MAX_VALUE));
328 
329             LargeSafeUnion safeUnion = safeunionInterface.newLargeSafeUnion();
330             safeUnion = safeunionInterface.setF(safeUnion, testArray);
331             ExpectTrue(safeUnion.getDiscriminator() == LargeSafeUnion.hidl_discriminator.f);
332             ExpectDeepEq(testArray, safeUnion.f());
333 
334             safeUnion = safeunionInterface.newLargeSafeUnion();
335             safeUnion = safeunionInterface.setI(safeUnion, testVector);
336             ExpectTrue(safeUnion.getDiscriminator() == LargeSafeUnion.hidl_discriminator.i);
337             ExpectDeepEq(testVector, safeUnion.i());
338         }
339         {
340             // SafeUnionStringTypeTest
341             String testString = "This is an inordinately long test string.";
342 
343             LargeSafeUnion safeUnion = safeunionInterface.newLargeSafeUnion();
344             safeUnion = safeunionInterface.setG(safeUnion, testString);
345             ExpectTrue(safeUnion.getDiscriminator() == LargeSafeUnion.hidl_discriminator.g);
346             ExpectDeepEq(testString, safeUnion.g());
347         }
348         {
349             // SafeUnionNestedTest
350             SmallSafeUnion smallSafeUnion = new SmallSafeUnion();
351             smallSafeUnion.a((byte) 1);
352 
353             LargeSafeUnion safeUnion = safeunionInterface.newLargeSafeUnion();
354             safeUnion = safeunionInterface.setL(safeUnion, smallSafeUnion);
355             ExpectTrue(safeUnion.getDiscriminator() == LargeSafeUnion.hidl_discriminator.l);
356             ExpectTrue(safeUnion.l().getDiscriminator() == SmallSafeUnion.hidl_discriminator.a);
357             ExpectTrue(safeUnion.l().a() == (byte) 1);
358         }
359         {
360             // SafeUnionEnumTest
361             LargeSafeUnion safeUnion = safeunionInterface.newLargeSafeUnion();
362             safeUnion = safeunionInterface.setM(safeUnion, ISafeUnion.BitField.V1);
363             ExpectTrue(safeUnion.getDiscriminator() == LargeSafeUnion.hidl_discriminator.m);
364             ExpectTrue(safeUnion.m() == ISafeUnion.BitField.V1);
365         }
366         {
367             // SafeUnionBitFieldTest
368             LargeSafeUnion safeUnion = safeunionInterface.newLargeSafeUnion();
369             safeUnion = safeunionInterface.setN(safeUnion, ISafeUnion.BitField.V1);
370             ExpectTrue(safeUnion.getDiscriminator() == LargeSafeUnion.hidl_discriminator.n);
371             ExpectTrue(safeUnion.n() == ISafeUnion.BitField.V1);
372         }
373         {
374             // SafeUnionInterfaceNullNativeHandleTest
375             InterfaceTypeSafeUnion safeUnion = new InterfaceTypeSafeUnion();
376 
377             safeUnion = safeunionInterface.setInterfaceF(safeUnion, null);
378             ExpectTrue(safeUnion.getDiscriminator() == InterfaceTypeSafeUnion.hidl_discriminator.f);
379             ExpectTrue(safeUnion.f() == null);
380         }
381         {
382             // SafeUnionInterfaceTest
383             byte[] testArray = new byte[] {-1, -2, -3, 0, 1, 2, 3};
384             ArrayList<String> testVector = new ArrayList(Arrays.asList("So", "Many", "Words"));
385             String testStringA = "Hello";
386             String testStringB = "World";
387 
388             ArrayList<NativeHandle> testHandlesVector = new ArrayList<>();
389             for (int i = 0; i < 128; i++) {
390                 testHandlesVector.add(new NativeHandle());
391             }
392 
393             InterfaceTypeSafeUnion safeUnion = safeunionInterface.newInterfaceTypeSafeUnion();
394             safeUnion = safeunionInterface.setInterfaceB(safeUnion, testArray);
395             ExpectTrue(safeUnion.getDiscriminator() == InterfaceTypeSafeUnion.hidl_discriminator.b);
396             ExpectDeepEq(testArray, safeUnion.b());
397 
398             IServiceManager anInterface = IServiceManager.getService();
399             safeUnion.c(anInterface);
400             ExpectTrue(safeUnion.getDiscriminator() == InterfaceTypeSafeUnion.hidl_discriminator.c);
401             ExpectTrue(HidlSupport.interfacesEqual(anInterface, safeUnion.c()));
402 
403             safeUnion = safeunionInterface.setInterfaceD(safeUnion, testStringA);
404             ExpectTrue(safeUnion.getDiscriminator() == InterfaceTypeSafeUnion.hidl_discriminator.d);
405             Expect(testStringA, safeUnion.d());
406 
407             safeUnion = safeunionInterface.setInterfaceE(safeUnion, testVector);
408             ExpectTrue(safeUnion.getDiscriminator() == InterfaceTypeSafeUnion.hidl_discriminator.e);
409             ExpectDeepEq(testVector, safeUnion.e());
410 
411             safeUnion = safeunionInterface.setInterfaceG(safeUnion, testHandlesVector);
412             ExpectTrue(safeUnion.getDiscriminator() == InterfaceTypeSafeUnion.hidl_discriminator.g);
413             ExpectTrue(safeUnion.g().size() == testHandlesVector.size());
414 
415             for (int i = 0; i < testHandlesVector.size(); i++) {
416                 ExpectFalse(safeUnion.g().get(i).hasSingleFileDescriptor());
417             }
418         }
419         {
420             // SafeUnionNullNativeHandleTest
421             HandleTypeSafeUnion safeUnion = new HandleTypeSafeUnion();
422 
423             safeUnion = safeunionInterface.setHandleA(safeUnion, null);
424             ExpectTrue(safeUnion.getDiscriminator() == HandleTypeSafeUnion.hidl_discriminator.a);
425             ExpectTrue(safeUnion.a() == null);
426         }
427         {
428             // SafeUnionDefaultNativeHandleTest
429             NativeHandle[] testHandlesArray = new NativeHandle[5];
430             for (int i = 0; i < testHandlesArray.length; i++) {
431                 testHandlesArray[i] = new NativeHandle();
432             }
433 
434             ArrayList<NativeHandle> testHandlesList = new ArrayList<NativeHandle>(
435                 Arrays.asList(testHandlesArray));
436 
437             HandleTypeSafeUnion safeUnion = safeunionInterface.newHandleTypeSafeUnion();
438             safeUnion = safeunionInterface.setHandleA(safeUnion, new NativeHandle());
439             ExpectTrue(safeUnion.getDiscriminator() == HandleTypeSafeUnion.hidl_discriminator.a);
440             ExpectFalse(safeUnion.a().hasSingleFileDescriptor());
441 
442             safeUnion = safeunionInterface.setHandleB(safeUnion, testHandlesArray);
443             ExpectTrue(safeUnion.getDiscriminator() == HandleTypeSafeUnion.hidl_discriminator.b);
444             ExpectTrue(safeUnion.b().length == testHandlesArray.length);
445 
446             for (int i = 0; i < testHandlesArray.length; i++) {
447                 ExpectFalse(safeUnion.b()[i].hasSingleFileDescriptor());
448             }
449 
450             safeUnion = safeunionInterface.setHandleC(safeUnion, testHandlesList);
451             ExpectTrue(safeUnion.getDiscriminator() == HandleTypeSafeUnion.hidl_discriminator.c);
452             ExpectTrue(safeUnion.c().size() == testHandlesList.size());
453 
454             for (int i = 0; i < testHandlesList.size(); i++) {
455                 ExpectFalse(safeUnion.c().get(i).hasSingleFileDescriptor());
456             }
457         }
458         {
459             // SafeUnionNativeHandleWithFdTest
460             final String testFileName = "/data/local/tmp/SafeUnionNativeHandleWithFdTest";
461             final String[] testStrings = {"This ", "is ", "so ", "much ", "data!\n"};
462             File file = new File(testFileName);
463 
464             if (file.exists()) { ExpectTrue(file.delete()); }
465             ExpectTrue(file.createNewFile());
466 
467             StringBuilder builder = new StringBuilder();
468             for (String testString : testStrings) {
469                 builder.append(testString);
470             }
471             final String goldenResult = builder.toString();
472 
473             ArrayList<NativeHandle> testHandlesList = new ArrayList<NativeHandle>();
474             FileOutputStream fos = new FileOutputStream(file);
475             for (int i = 0; i < testStrings.length; i++) {
476                 testHandlesList.add(new NativeHandle(fos.getFD(), false /*own*/));
477             }
478 
479             HandleTypeSafeUnion safeUnion = safeunionInterface.newHandleTypeSafeUnion();
480             safeUnion = safeunionInterface.setHandleC(safeUnion, testHandlesList);
481             for (int i = 0; i < safeUnion.c().size(); i++) {
482                 ExpectTrue(safeUnion.c().get(i).hasSingleFileDescriptor());
483 
484                 // If you want to copy it out of the binder buffer or save it, it needs to be duped.
485                 // This isn't necessary for the test since it is kept open for the binder window.
486                 NativeHandle handle = safeUnion.c().get(i);
487                 if (i%2 == 0) handle = handle.dup();
488 
489                 // Original fd is duped if not dup'd above
490                 FileDescriptor resultFd = handle.getFileDescriptor();
491                 ExpectTrue(resultFd.getInt$() != fos.getFD().getInt$());
492 
493                 FileOutputStream otherFos = new FileOutputStream(resultFd);
494                 otherFos.write(testStrings[i].getBytes());
495                 otherFos.flush();
496 
497                 otherFos.close();
498 
499                 if (i%2 == 0) handle.close();
500             }
501 
502             byte[] resultData = new byte[(int) file.length()];
503             FileInputStream fis = new FileInputStream(file);
504             fis.read(resultData);
505 
506             String result = new String(resultData);
507             Expect(result, goldenResult);
508 
509             fis.close();
510             fos.close();
511             ExpectTrue(file.delete());
512         }
513         {
514             // SafeUnionEqualityTest
515             LargeSafeUnion one = safeunionInterface.newLargeSafeUnion();
516             LargeSafeUnion two = safeunionInterface.newLargeSafeUnion();
517             ExpectTrue(one.equals(two));
518 
519             one = safeunionInterface.setA(one, (byte) 1);
520             ExpectFalse(one.equals(two));
521 
522             two = safeunionInterface.setB(two, (byte) 1);
523             ExpectFalse(one.equals(two));
524 
525             two = safeunionInterface.setA(two, (byte) 2);
526             ExpectFalse(one.equals(two));
527 
528             two = safeunionInterface.setA(two, (byte) 1);
529             ExpectTrue(one.equals(two));
530         }
531         {
532             // SafeUnionDeepEqualityTest
533             ArrayList<Long> testVectorA = new ArrayList(Arrays.asList(1L, 2L, 3L));
534             ArrayList<Long> testVectorB = new ArrayList(Arrays.asList(2L, 1L, 3L));
535 
536             LargeSafeUnion one = safeunionInterface.newLargeSafeUnion();
537             LargeSafeUnion two = safeunionInterface.newLargeSafeUnion();
538 
539             one = safeunionInterface.setI(one, testVectorA);
540             two = safeunionInterface.setI(two, testVectorB);
541             ExpectFalse(one.equals(two));
542 
543             two = safeunionInterface.setI(two, (ArrayList<Long>) testVectorA.clone());
544             ExpectTrue(one.equals(two));
545         }
546         {
547             // SafeUnionHashCodeTest
548             ArrayList<Boolean> testVector =
549                 new ArrayList(Arrays.asList(true, false, false, true, true));
550 
551             LargeSafeUnion one = safeunionInterface.newLargeSafeUnion();
552             LargeSafeUnion two = safeunionInterface.newLargeSafeUnion();
553 
554             one = safeunionInterface.setH(one, testVector);
555             two = safeunionInterface.setA(two, (byte) -5);
556             ExpectFalse(one.hashCode() == two.hashCode());
557 
558             two = safeunionInterface.setH(two, (ArrayList<Boolean>) testVector.clone());
559             ExpectTrue(one.hashCode() == two.hashCode());
560         }
561     }
562 
client()563     private void client() throws RemoteException, IOException, ErrnoException {
564 
565         ExpectDeepEq(null, null);
566         ExpectDeepNe(null, new String());
567         ExpectDeepNe(new String(), null);
568         ExpectDeepEq(new String(), new String());
569         ExpectDeepEq("hey", "hey");
570 
571         ExpectDeepEq(new int[]{1,2}, new int[]{1,2});
572         ExpectDeepNe(new int[]{1,2}, new int[]{1,3});
573         ExpectDeepNe(new int[]{1,2}, new int[]{1,2,3});
574         ExpectDeepEq(new int[][]{{1,2},{3,4}}, new int[][]{{1,2},{3,4}});
575         ExpectDeepNe(new int[][]{{1,2},{3,4}}, new int[][]{{1,2},{3,5}});
576         ExpectDeepNe(new int[][]{{1,2},{3,4}}, new int[][]{{1,2,3},{4,5,6}});
577         ExpectDeepNe(new int[][]{{1,2},{3,4}}, new int[][]{{1,2},{3,4,5}});
578 
579         ExpectDeepEq(new Integer[]{1,2}, new Integer[]{1,2});
580         ExpectDeepNe(new Integer[]{1,2}, new Integer[]{1,3});
581         ExpectDeepNe(new Integer[]{1,2}, new Integer[]{1,2,3});
582         ExpectDeepEq(new Integer[][]{{1,2},{3,4}}, new Integer[][]{{1,2},{3,4}});
583         ExpectDeepNe(new Integer[][]{{1,2},{3,4}}, new Integer[][]{{1,2},{3,5}});
584         ExpectDeepNe(new Integer[][]{{1,2},{3,4}}, new Integer[][]{{1,2,3},{4,5,6}});
585         ExpectDeepNe(new Integer[][]{{1,2},{3,4}}, new Integer[][]{{1,2},{3,4,5}});
586 
587         ExpectDeepEq(new ArrayList(Arrays.asList(1, 2)),
588                      new ArrayList(Arrays.asList(1, 2)));
589         ExpectDeepNe(new ArrayList(Arrays.asList(1, 2)),
590                      new ArrayList(Arrays.asList(1, 2, 3)));
591 
592         ExpectDeepEq(new ArrayList(Arrays.asList(new int[]{1,2}, new int[]{3,4})),
593                      new ArrayList(Arrays.asList(new int[]{1,2}, new int[]{3,4})));
594         ExpectDeepNe(new ArrayList(Arrays.asList(new int[]{1,2}, new int[]{3,4})),
595                      new ArrayList(Arrays.asList(new int[]{1,2}, new int[]{3,5})));
596 
597         ExpectDeepEq(new ArrayList(Arrays.asList(new Integer[]{1,2}, new Integer[]{3,4})),
598                      new ArrayList(Arrays.asList(new Integer[]{1,2}, new Integer[]{3,4})));
599         ExpectDeepNe(new ArrayList(Arrays.asList(new Integer[]{1,2}, new Integer[]{3,4})),
600                      new ArrayList(Arrays.asList(new Integer[]{1,2}, new Integer[]{3,5})));
601 
602         ExpectDeepEq(new ArrayList[]{new ArrayList(Arrays.asList(1,2)),
603                                      new ArrayList(Arrays.asList(3,4))},
604                      new ArrayList[]{new ArrayList(Arrays.asList(1,2)),
605                                      new ArrayList(Arrays.asList(3,4))});
606 
607         {
608             // Test proper exceptions are thrown
609             try {
610                 IBase proxy = IBase.getService("this-doesn't-exist");
611                 // this should never run
612                 ExpectTrue(false);
613             } catch (Exception e) {
614                 ExpectTrue(e instanceof NoSuchElementException);
615             }
616         }
617 
618         {
619             // Test proper exceptions are thrown
620             try {
621                 // not in manifest, so won't wait
622                 IBase proxy = IBase.getService("this-doesn't-exist", true /*retry*/);
623                 // this should never run
624                 ExpectTrue(false);
625             } catch (Exception e) {
626                 ExpectTrue(e instanceof NoSuchElementException);
627             }
628         }
629 
630         {
631             // Test access through base interface binder.
632             IBase baseProxy = IBase.getService();
633             baseProxy.someBaseMethod();
634 
635             IBaz bazProxy = IBaz.castFrom(baseProxy);
636             ExpectTrue(bazProxy != null);
637 
638             // IQuux is completely unrelated to IBase/IBaz, so the following
639             // should fail, i.e. return null.
640             IQuux quuxProxy = IQuux.castFrom(baseProxy);
641             ExpectTrue(quuxProxy == null);
642         }
643 
644         {
645             // Test waiting API
646             IBase baseProxyA = IBaz.getService(true /* retry */);
647             ExpectTrue(baseProxyA != null);
648             IBase baseProxyB = IBaz.getService(false /* retry */);
649             ExpectTrue(baseProxyB != null);
650         }
651 
652         IBaz proxy = IBaz.getService();
653 
654         proxy.ping();
655 
656         proxy.someBaseMethod();
657 
658         {
659             Expect(proxy.interfaceDescriptor(), IBaz.kInterfaceName);
660         }
661 
662         {
663             // Tests calling a two-way method with oneway enabled.
664             IHwBinder binder = proxy.asBinder();
665             HwParcel request = new HwParcel();
666             HwParcel reply = new HwParcel();
667 
668             request.writeInterfaceToken(IBaz.kInterfaceName);
669             request.writeInt64(1234);
670             // IBaz::doThatAndReturnSomething is not oneway but we call it using FLAG_ONEWAY.
671             binder.transact(19 /*doThatAndReturnSomething*/, request, reply, IBinder.FLAG_ONEWAY);
672 
673             try {
674                 reply.verifySuccess();
675                 // This should never run.
676                 ExpectTrue(false);
677             } catch (Exception e) {
678                 ExpectTrue(e instanceof RemoteException);
679             }
680 
681             proxy.ping();
682         }
683 
684         {
685             // Tests calling a oneway method with oneway disabled.
686             IHwBinder binder = proxy.asBinder();
687             HwParcel request = new HwParcel();
688             HwParcel reply = new HwParcel();
689 
690             request.writeInterfaceToken(IBaz.kInterfaceName);
691             request.writeFloat(1.0f);
692             // IBaz::doThis is oneway but we call it without using FLAG_ONEWAY.
693             // This does not raise an exception in C++ because
694             // IPCThreadState::executeCommand for BR_TRANSACTION sends an empty
695             // reply for two-way transactions if the transaction itself did not
696             // send a reply.
697             try {
698                 binder.transact(18 /*doThis*/, request, reply, 0 /* Not FLAG_ONEWAY */);
699                 ExpectTrue(!proxy.isJava());
700             } catch (RemoteException e) {
701                 ExpectTrue(proxy.isJava());
702             }
703 
704             proxy.ping();
705         }
706 
707         {
708             IBase.Foo foo = new IBase.Foo();
709             foo.x = 1;
710 
711             for (int i = 0; i < 5; ++i) {
712                 IBase.Foo.Bar bar = new IBase.Foo.Bar();
713                 bar.z = 1.0f + (float)i * 0.01f;
714                 bar.s = "Hello, world " + i;
715                 foo.aaa.add(bar);
716             }
717 
718             foo.y.z = 3.14f;
719             foo.y.s = "Lorem ipsum...";
720 
721             IBase.Foo result = proxy.someOtherBaseMethod(foo);
722             ExpectTrue(result.equals(foo));
723         }
724 
725         {
726             IBase.Foo[] inputArray = new IBase.Foo[2];
727 
728             IBase.Foo foo = new IBase.Foo();
729             foo.x = 1;
730 
731             for (int i = 0; i < 5; ++i) {
732                 IBase.Foo.Bar bar = new IBase.Foo.Bar();
733                 bar.z = 1.0f + (float)i * 0.01f;
734                 bar.s = "Hello, world " + i;
735                 foo.aaa.add(bar);
736             }
737 
738             foo.y.z = 3.14f;
739             foo.y.s = "Lorem ipsum...";
740 
741             inputArray[0] = foo;
742 
743             foo = new IBase.Foo();
744             foo.x = 2;
745 
746             for (int i = 0; i < 3; ++i) {
747                 IBase.Foo.Bar bar = new IBase.Foo.Bar();
748                 bar.z = 2.0f - (float)i * 0.01f;
749                 bar.s = "Lorem ipsum " + i;
750                 foo.aaa.add(bar);
751             }
752 
753             foo.y.z = 1.1414f;
754             foo.y.s = "Et tu brute?";
755 
756             inputArray[1] = foo;
757 
758             IBase.Foo[] expectedOutputArray = new IBase.Foo[2];
759             expectedOutputArray[0] = inputArray[1];
760             expectedOutputArray[1] = inputArray[0];
761 
762             IBase.Foo[] outputArray = proxy.someMethodWithFooArrays(inputArray);
763 
764             ExpectTrue(java.util.Objects.deepEquals(outputArray, expectedOutputArray));
765         }
766 
767         {
768             ArrayList<IBase.Foo> inputVec = new ArrayList<IBase.Foo>();
769 
770             IBase.Foo foo = new IBase.Foo();
771             foo.x = 1;
772 
773             for (int i = 0; i < 5; ++i) {
774                 IBase.Foo.Bar bar = new IBase.Foo.Bar();
775                 bar.z = 1.0f + (float)i * 0.01f;
776                 bar.s = "Hello, world " + i;
777                 foo.aaa.add(bar);
778             }
779 
780             foo.y.z = 3.14f;
781             foo.y.s = "Lorem ipsum...";
782 
783             inputVec.add(foo);
784 
785             foo = new IBase.Foo();
786             foo.x = 2;
787 
788             for (int i = 0; i < 3; ++i) {
789                 IBase.Foo.Bar bar = new IBase.Foo.Bar();
790                 bar.z = 2.0f - (float)i * 0.01f;
791                 bar.s = "Lorem ipsum " + i;
792                 foo.aaa.add(bar);
793             }
794 
795             foo.y.z = 1.1414f;
796             foo.y.s = "Et tu brute?";
797 
798             inputVec.add(foo);
799 
800             ArrayList<IBase.Foo> expectedOutputVec = new ArrayList<IBase.Foo>();
801             expectedOutputVec.add(inputVec.get(1));
802             expectedOutputVec.add(inputVec.get(0));
803 
804             ArrayList<IBase.Foo> outputVec =
805                 proxy.someMethodWithFooVectors(inputVec);
806 
807             ExpectTrue(java.util.Objects.deepEquals(outputVec, expectedOutputVec));
808         }
809 
810         {
811             IBase.VectorOfArray in = new IBase.VectorOfArray();
812 
813             int k = 0;
814             for (int i = 0; i < 3; ++i) {
815                 byte[] mac = new byte[6];
816                 for (int j = 0; j < 6; ++j, ++k) {
817                     mac[j] = (byte)k;
818                 }
819 
820                 in.addresses.add(mac);
821             }
822 
823             IBase.VectorOfArray expectedOut = new IBase.VectorOfArray();
824             int n = in.addresses.size();
825 
826             for (int i = 0; i < n; ++i) {
827                 expectedOut.addresses.add(in.addresses.get(n - 1 - i));
828             }
829 
830             IBase.VectorOfArray out = proxy.someMethodWithVectorOfArray(in);
831             ExpectTrue(out.equals(expectedOut));
832         }
833 
834         {
835             ArrayList<byte[]> in = new ArrayList<byte[]>();
836 
837             int k = 0;
838             for (int i = 0; i < 3; ++i) {
839                 byte[] mac = new byte[6];
840                 for (int j = 0; j < 6; ++j, ++k) {
841                     mac[j] = (byte)k;
842                 }
843 
844                 in.add(mac);
845             }
846 
847             ArrayList<byte[]> expectedOut = new ArrayList<byte[]>();
848 
849             int n = in.size();
850             for (int i = 0; i < n; ++i) {
851                 expectedOut.add(in.get(n - 1 - i));
852             }
853 
854             ArrayList<byte[]> out = proxy.someMethodTakingAVectorOfArray(in);
855 
856             ExpectTrue(out.size() == expectedOut.size());
857             for  (int i = 0; i < n; ++i) {
858                 ExpectTrue(java.util.Objects.deepEquals(out.get(i), expectedOut.get(i)));
859             }
860         }
861 
862         {
863             IBase.StringMatrix5x3 in = new IBase.StringMatrix5x3();
864             IBase.StringMatrix3x5 expectedOut = new IBase.StringMatrix3x5();
865 
866             for (int i = 0; i < 5; ++i) {
867                 for (int j = 0; j < 3; ++j) {
868                     in.s[i][j] = numberToEnglish(3 * i + j + 1);
869                     expectedOut.s[j][i] = in.s[i][j];
870                 }
871             }
872 
873             IBase.StringMatrix3x5 out = proxy.transpose(in);
874 
875             // [[1 2 3] [4 5 6] [7 8 9] [10 11 12] [13 14 15]]^T
876             // = [[1 4 7 10 13] [2 5 8 11 14] [3 6 9 12 15]]
877             ExpectTrue(out.equals(expectedOut));
878         }
879 
880         {
881             String[][] in = new String[5][3];
882             String[][] expectedOut = new String[3][5];
883             for (int i = 0; i < 5; ++i) {
884                 for (int j = 0; j < 3; ++j) {
885                     in[i][j] = numberToEnglish(3 * i + j + 1);
886                     expectedOut[j][i] = in[i][j];
887                 }
888             }
889 
890             String[][] out = proxy.transpose2(in);
891 
892             // [[1 2 3] [4 5 6] [7 8 9] [10 11 12] [13 14 15]]^T
893             // = [[1 4 7 10 13] [2 5 8 11 14] [3 6 9 12 15]]
894             ExpectTrue(java.util.Arrays.deepEquals(out, expectedOut));
895         }
896 
897         ExpectTrue(proxy.someBoolMethod(true) == false);
898 
899         {
900             boolean[] someBoolArray = new boolean[3];
901             someBoolArray[0] = true;
902             someBoolArray[1] = false;
903             someBoolArray[2] = true;
904 
905             boolean[] resultArray = proxy.someBoolArrayMethod(someBoolArray);
906             ExpectTrue(resultArray[0] == false);
907             ExpectTrue(resultArray[1] == true);
908             ExpectTrue(resultArray[2] == false);
909 
910             ArrayList<Boolean> someBoolVec = new ArrayList<Boolean>();
911             someBoolVec.add(true);
912             someBoolVec.add(false);
913             someBoolVec.add(true);
914 
915             ArrayList<Boolean> resultVec = proxy.someBoolVectorMethod(someBoolVec);
916             ExpectTrue(resultVec.get(0) == false);
917             ExpectTrue(resultVec.get(1) == true);
918             ExpectTrue(resultVec.get(2) == false);
919         }
920 
921         proxy.doThis(1.0f);
922 
923         ExpectTrue(proxy.doThatAndReturnSomething(1) == 666);
924         ExpectTrue(proxy.doQuiteABit(1, 2L, 3.0f, 4.0) == 666.5);
925 
926         {
927             int[] paramArray = new int[15];
928             int[] expectedOutArray = new int[32];
929             ArrayList<Integer> paramVec = new ArrayList<Integer>();
930             ArrayList<Integer> expectedOutVec = new ArrayList<Integer>();
931 
932             for (int i = 0; i < paramArray.length; ++i) {
933                 paramArray[i] = i;
934                 paramVec.add(i);
935 
936                 expectedOutArray[i] = 2 * i;
937                 expectedOutArray[15 + i] = i;
938 
939                 expectedOutVec.add(2 * i);
940             }
941 
942             expectedOutArray[30] = 1;
943             expectedOutArray[31] = 2;
944 
945 
946             int[] outArray = proxy.doSomethingElse(paramArray);
947             ExpectTrue(java.util.Objects.deepEquals(outArray, expectedOutArray));
948 
949             ArrayList<Integer> outVec = proxy.mapThisVector(paramVec);
950             ExpectTrue(java.util.Objects.equals(outVec, expectedOutVec));
951         }
952 
953         Expect(proxy.doStuffAndReturnAString(), "Hello, world!");
954 
955         BazCallback cb = new BazCallback();
956         ExpectTrue(!cb.wasCalled());
957         proxy.callMe(cb);
958         ExpectTrue(cb.wasCalled());
959 
960         ExpectTrue(proxy.useAnEnum(IBaz.SomeEnum.goober) == IBaz.SomeEnum.quux);
961 
962         {
963             String[] stringArray = new String[3];
964             stringArray[0] = "one";
965             stringArray[1] = "two";
966             stringArray[2] = "three";
967 
968             String[] expectedOutArray = new String[2];
969             expectedOutArray[0] = "Hello";
970             expectedOutArray[1] = "World";
971 
972             String[] outArray = proxy.haveSomeStrings(stringArray);
973             ExpectTrue(java.util.Arrays.deepEquals(outArray, expectedOutArray));
974 
975             ArrayList<String> stringVec = new ArrayList<String>();
976             stringVec.add("one");
977             stringVec.add("two");
978             stringVec.add("three");
979 
980             ArrayList<String> expectedOutVec = new ArrayList<String>();
981             expectedOutVec.add("Hello");
982             expectedOutVec.add("World");
983 
984             ExpectTrue(expectedOutVec.equals(proxy.haveAStringVec(stringVec)));
985         }
986 
987         {
988             ArrayList<Byte> bytes = new ArrayList<Byte>();
989             bytes.add(IBaz.BitField.V1);
990             bytes.add(IBaz.BitField.V2);
991             ExpectTrue(bytes.equals(proxy.repeatBitfieldVec(bytes)));
992         }
993 
994         proxy.returnABunchOfStrings(
995                 new IBaz.returnABunchOfStringsCallback() {
996                     @Override
997                     public void onValues(String a, String b, String c) {
998                         Expect(a, "Eins");
999                         Expect(b, "Zwei");
1000                         Expect(c, "Drei");
1001                     }
1002                 });
1003 
1004         proxy.returnABunchOfStrings((a,b,c) -> Expect(a + b + c, "EinsZweiDrei"));
1005 
1006         proxy.callMeLater(new BazCallback());
1007         System.gc();
1008         proxy.iAmFreeNow();
1009 
1010         {
1011             IBaz.T t1 = new IBaz.T();
1012             IBaz.T t2 = new IBaz.T();
1013             for (int i = 0; i < 5; i++) {
1014                 for (int j = 0; j < 3; j++) {
1015                     t1.matrix5x3[i][j] = t2.matrix5x3[i][j] = (i + 1) * (j + 1);
1016                 }
1017             }
1018             ExpectTrue(t1.equals(t2));
1019             ExpectTrue(t1.hashCode() == t2.hashCode());
1020             t2.matrix5x3[4][2] = -60;
1021             ExpectTrue(!t1.equals(t2));
1022         }
1023 
1024         // server currently only implements this in C++
1025         if (!proxy.isJava()) {
1026             ArrayList<NestedStruct> structs = proxy.getNestedStructs();
1027             ExpectTrue(structs.size() == 5);
1028             ExpectTrue(structs.get(1).matrices.size() == 6);
1029         }
1030 
1031         {
1032             IBaz.Everything e = new IBaz.Everything();
1033             Expect(e.toString(),
1034                 "{.number = 0, .anotherNumber = 0, .s = , " +
1035                 ".vs = [], .multidimArray = [[null, null], [null, null]], " +
1036                 ".sArray = [null, null, null], .anotherStruct = {.first = , .last = }, .bf = }");
1037             e.s = "string!";
1038             e.number = 127;
1039             e.anotherNumber = 100;
1040             e.vs.addAll(Arrays.asList("One", "Two", "Three"));
1041             for (int i = 0; i < e.multidimArray.length; i++)
1042                 for (int j = 0; j < e.multidimArray[i].length; j++)
1043                     e.multidimArray[i][j] = Integer.toString(i) + Integer.toString(j);
1044             e.bf = IBaz.BitField.VALL;
1045             e.anotherStruct.first = "James";
1046             e.anotherStruct.last = "Bond";
1047             Expect(e.toString(),
1048                 "{.number = 127, .anotherNumber = 100, .s = string!, " +
1049                 ".vs = [One, Two, Three], .multidimArray = [[00, 01], [10, 11]], " +
1050                 ".sArray = [null, null, null], .anotherStruct = {.first = James, .last = Bond}, " +
1051                 ".bf = V0 | V1 | V2 | V3 | VALL}");
1052             Expect(IBaz.BitField.toString(IBaz.BitField.VALL), "VALL");
1053             Expect(IBaz.BitField.toString((byte)(IBaz.BitField.V0 | IBaz.BitField.V2)), "0x5");
1054             Expect(IBaz.BitField.dumpBitfield(IBaz.BitField.VALL), "V0 | V1 | V2 | V3 | VALL");
1055             Expect(IBaz.BitField.dumpBitfield((byte)(IBaz.BitField.V1 | IBaz.BitField.V3 | 0xF0)),
1056                 "V1 | V3 | 0xf0");
1057 
1058             Expect(proxy.toString(), IBaz.kInterfaceName + "@Proxy");
1059         }
1060 
1061         {
1062             // Ensure that native parcel is cleared even if the corresponding
1063             // Java object isn't GC'd.
1064             ArrayList<Integer> data4K = new ArrayList<>(1024);
1065             for (int i = 0; i < 1024; i++) {
1066                 data4K.add(i);
1067             }
1068 
1069             for (int i = 0; i < 1024; i++) {
1070                 // If they are not properly cleaned up, these calls will put 4MB of data in
1071                 // kernel binder buffer, and will fail.
1072                 try {
1073                     proxy.mapThisVector(data4K);
1074                 } catch (RemoteException ex) {
1075                     throw new RuntimeException("Failed at call #" + Integer.toString(i), ex);
1076                 }
1077             }
1078         }
1079 
1080         {
1081             // TestArrays
1082             IBase.LotsOfPrimitiveArrays in = new IBase.LotsOfPrimitiveArrays();
1083 
1084             for (int i = 0; i < 128; ++i) {
1085                 in.byte1[i] = (byte)i;
1086                 in.boolean1[i] = (i & 4) != 0;
1087                 in.double1[i] = i;
1088             }
1089 
1090             int m = 0;
1091             for (int i = 0; i < 8; ++i) {
1092                 for (int j = 0; j < 128; ++j, ++m) {
1093                     in.byte2[i][j] = (byte)m;
1094                     in.boolean2[i][j] = (m & 4) != 0;
1095                     in.double2[i][j] = m;
1096                 }
1097             }
1098 
1099             m = 0;
1100             for (int i = 0; i < 8; ++i) {
1101                 for (int j = 0; j < 16; ++j) {
1102                     for (int k = 0; k < 128; ++k, ++m) {
1103                         in.byte3[i][j][k] = (byte)m;
1104                         in.boolean3[i][j][k] = (m & 4) != 0;
1105                         in.double3[i][j][k] = m;
1106                     }
1107                 }
1108             }
1109 
1110             IBase.LotsOfPrimitiveArrays out = proxy.testArrays(in);
1111 
1112             final double PRECISION = 0.00001f;
1113 
1114             ExpectDeepEq(in.byte1, out.byte1);
1115             ExpectDeepEq(in.byte2, out.byte2);
1116             ExpectDeepEq(in.byte3, out.byte3);
1117             ExpectDeepEq(in.boolean1, out.boolean1);
1118             ExpectDeepEq(in.boolean2, out.boolean2);
1119             ExpectDeepEq(in.boolean3, out.boolean3);
1120             for (int i = 0; i < 128; ++i) {
1121                 ExpectWithin(in.double1[i], out.double1[i], PRECISION, String.format("i = %d", i));
1122             }
1123             for (int i = 0; i < 8; ++i) {
1124                 for (int j = 0; j < 128; ++j) {
1125                     ExpectWithin(in.double2[i][j], out.double2[i][j], PRECISION,
1126                             String.format("i = %d, j = %d", i, j));
1127                 }
1128             }
1129             for (int i = 0; i < 8; ++i) {
1130                 for (int j = 0; j < 16; ++j) {
1131                     for (int k = 0; k < 128; ++k) {
1132                         ExpectWithin(in.double3[i][j][k], out.double3[i][j][k], PRECISION,
1133                                 String.format("i = %d, j = %d, k = %d", i, j, k));
1134                     }
1135                 }
1136             }
1137             ExpectDeepEq(in.double1, out.double1);
1138             ExpectDeepEq(in.double2, out.double2);
1139             ExpectDeepEq(in.double3, out.double3);
1140             ExpectDeepEq(in, out);
1141         }
1142 
1143         {
1144             // testByteVecs
1145 
1146             ArrayList<byte[]> in = new ArrayList<byte[]>();
1147 
1148             int k = 0;
1149             for (int i = 0; i < 8; ++i) {
1150                 byte[] elem = new byte[128];
1151                 for (int j = 0; j < 128; ++j, ++k) {
1152                     elem[j] = (byte)k;
1153                 }
1154                 in.add(elem);
1155             }
1156 
1157             ArrayList<byte[]> out = proxy.testByteVecs(in);
1158 
1159             ExpectDeepEq(in, out);
1160         }
1161 
1162         {
1163             // testByteVecs w/ mismatched element lengths.
1164 
1165             ArrayList<byte[]> in = new ArrayList<byte[]>();
1166 
1167             int k = 0;
1168             for (int i = 0; i < 8; ++i) {
1169                 byte[] elem = new byte[128 - i];
1170                 for (int j = 0; j < (128 - i); ++j, ++k) {
1171                     elem[j] = (byte)k;
1172                 }
1173                 in.add(elem);
1174             }
1175 
1176             boolean failedAsItShould = false;
1177 
1178             try {
1179                 ArrayList<byte[]> out = proxy.testByteVecs(in);
1180             }
1181             catch (IllegalArgumentException e) {
1182                 failedAsItShould = true;
1183             }
1184 
1185             ExpectTrue(failedAsItShould);
1186         }
1187 
1188         {
1189             // testBooleanVecs
1190 
1191             ArrayList<boolean[]> in = new ArrayList<boolean[]>();
1192 
1193             int k = 0;
1194             for (int i = 0; i < 8; ++i) {
1195                 boolean[] elem = new boolean[128];
1196                 for (int j = 0; j < 128; ++j, ++k) {
1197                     elem[j] = (k & 4) != 0;
1198                 }
1199                 in.add(elem);
1200             }
1201 
1202             ArrayList<boolean[]> out = proxy.testBooleanVecs(in);
1203             ExpectDeepEq(in, out);
1204         }
1205 
1206         {
1207             // testDoubleVecs
1208 
1209             ArrayList<double[]> in = new ArrayList<double[]>();
1210 
1211             int k = 0;
1212             for (int i = 0; i < 8; ++i) {
1213                 double[] elem = new double[128];
1214                 for (int j = 0; j < 128; ++j, ++k) {
1215                     elem[j] = k;
1216                 }
1217                 in.add(elem);
1218             }
1219 
1220             ArrayList<double[]> out = proxy.testDoubleVecs(in);
1221             ExpectDeepEq(in, out);
1222         }
1223         {
1224             // testProxyEquals
1225             // TODO(b/68727931): test passthrough services as well.
1226 
1227             IBase proxy1 = IBase.getService();
1228             IBase proxy2 = IBase.getService();
1229             IBaz proxy3 = IBaz.getService();
1230             IBazCallback callback1 = new BazCallback();
1231             IBazCallback callback2 = new BazCallback();
1232             IServiceManager manager = IServiceManager.getService();
1233 
1234             // test hwbinder proxies
1235             ExpectEqual(proxy1, proxy2); // same proxy class
1236             ExpectEqual(proxy1, proxy3); // different proxy class
1237 
1238             // negative tests
1239             ExpectNotEqual(proxy1, null);
1240             ExpectNotEqual(proxy1, callback1); // proxy != stub
1241             ExpectNotEqual(proxy1, manager);
1242 
1243             // HidlSupport.interfacesEqual use overridden .equals for stubs
1244             ExpectEqual(callback1, callback1);
1245             ExpectEqual(callback1, callback2);
1246             callback1.hey();
1247             ExpectNotEqual(callback1, callback2);
1248             callback2.hey();
1249             ExpectEqual(callback1, callback2);
1250 
1251             // test hash for proxies
1252             java.util.HashSet<IBase> set = new java.util.HashSet<>();
1253             set.add(proxy1);
1254             ExpectTrue(set.contains(proxy1)); // hash is stable
1255             ExpectTrue(set.contains(proxy2));
1256             ExpectFalse(set.contains(manager));
1257         }
1258         {
1259             IBaz baz = IBaz.getService();
1260             ExpectTrue(baz != null);
1261             IBaz.StructWithInterface swi = new IBaz.StructWithInterface();
1262             swi.iface = IServiceManager.getService();
1263             swi.number = 12345678;
1264             IBaz.StructWithInterface swi_back = baz.haveSomeStructWithInterface(swi);
1265             ExpectTrue(swi_back != null);
1266             ExpectTrue(swi_back.iface != null);
1267             ExpectTrue(HidlSupport.interfacesEqual(swi.iface, swi_back.iface));
1268             ExpectTrue(swi_back.number == 12345678);
1269         }
1270 
1271         runClientSafeUnionTests();
1272 
1273         // currently no Java implementation of this
1274         if (!proxy.isJava()) {
1275             runClientMemoryTests();
1276         }
1277 
1278         // --- DEATH RECIPIENT TESTING ---
1279         // This must always be done last, since it will kill the native server process
1280         HidlDeathRecipient recipient1 = new HidlDeathRecipient();
1281         HidlDeathRecipient recipient2 = new HidlDeathRecipient();
1282 
1283         final int cookie1 = 0x1481;
1284         final int cookie2 = 0x1482;
1285         final int cookie3 = 0x1483;
1286         ExpectTrue(proxy.linkToDeath(recipient1, cookie1));
1287 
1288         ExpectTrue(proxy.linkToDeath(recipient1, cookie3));
1289         ExpectTrue(proxy.unlinkToDeath(recipient1));
1290 
1291         ExpectTrue(proxy.linkToDeath(recipient2, cookie2));
1292         ExpectTrue(proxy.unlinkToDeath(recipient2));
1293         try {
1294             proxy.dieNow();
1295         } catch (DeadObjectException e) {
1296             // Expected
1297         }
1298         ExpectTrue(recipient1.waitUntilServiceDied(2000 /*timeoutMillis*/));
1299         ExpectTrue(!recipient2.waitUntilServiceDied(2000 /*timeoutMillis*/));
1300         ExpectTrue(recipient1.cookieMatches(cookie1));
1301         Log.d(TAG, "OK, exiting");
1302     }
1303 
1304     class Baz extends IBaz.Stub {
1305         // from IBase
isJava()1306         public boolean isJava() {
1307             Log.d(TAG, "Baz isJava");
1308             return true;
1309         }
1310 
someBaseMethod()1311         public void someBaseMethod() {
1312             Log.d(TAG, "Baz someBaseMethod");
1313         }
1314 
someOtherBaseMethod(IBase.Foo foo)1315         public IBase.Foo someOtherBaseMethod(IBase.Foo foo) {
1316             Log.d(TAG, "Baz someOtherBaseMethod " + foo.toString());
1317             return foo;
1318         }
1319 
someMethodWithFooArrays(IBase.Foo[] fooInput)1320         public IBase.Foo[] someMethodWithFooArrays(IBase.Foo[] fooInput) {
1321             Log.d(TAG, "Baz someMethodWithFooArrays " + Arrays.toString(fooInput));
1322 
1323             IBase.Foo[] fooOutput = new IBase.Foo[2];
1324             fooOutput[0] = fooInput[1];
1325             fooOutput[1] = fooInput[0];
1326 
1327             return fooOutput;
1328         }
1329 
someMethodWithFooVectors( ArrayList<IBase.Foo> fooInput)1330         public ArrayList<IBase.Foo> someMethodWithFooVectors(
1331                 ArrayList<IBase.Foo> fooInput) {
1332             Log.d(TAG, "Baz someMethodWithFooVectors " + fooInput.toString());
1333 
1334             ArrayList<IBase.Foo> fooOutput = new ArrayList<IBase.Foo>();
1335             fooOutput.add(fooInput.get(1));
1336             fooOutput.add(fooInput.get(0));
1337 
1338             return fooOutput;
1339         }
1340 
someMethodWithVectorOfArray( IBase.VectorOfArray in)1341         public IBase.VectorOfArray someMethodWithVectorOfArray(
1342                 IBase.VectorOfArray in) {
1343             Log.d(TAG, "Baz someMethodWithVectorOfArray " + in.toString());
1344 
1345             IBase.VectorOfArray out = new IBase.VectorOfArray();
1346             int n = in.addresses.size();
1347             for (int i = 0; i < n; ++i) {
1348                 out.addresses.add(in.addresses.get(n - i - 1));
1349             }
1350 
1351             return out;
1352         }
1353 
someMethodTakingAVectorOfArray( ArrayList<byte[ ]> in)1354         public ArrayList<byte[/* 6 */]> someMethodTakingAVectorOfArray(
1355                 ArrayList<byte[/* 6 */]> in) {
1356             Log.d(TAG, "Baz someMethodTakingAVectorOfArray");
1357 
1358             int n = in.size();
1359             ArrayList<byte[]> out = new ArrayList<byte[]>();
1360             for (int i = 0; i < n; ++i) {
1361                 out.add(in.get(n - i - 1));
1362             }
1363 
1364             return out;
1365         }
1366 
transpose(IBase.StringMatrix5x3 in)1367         public IBase.StringMatrix3x5 transpose(IBase.StringMatrix5x3 in) {
1368             Log.d(TAG, "Baz transpose " + in.toString());
1369 
1370             IBase.StringMatrix3x5 out = new IBase.StringMatrix3x5();
1371             for (int i = 0; i < 3; ++i) {
1372                 for (int j = 0; j < 5; ++j) {
1373                     out.s[i][j] = in.s[j][i];
1374                 }
1375             }
1376 
1377             return out;
1378         }
1379 
transpose2(String[][] in)1380         public String[][] transpose2(String[][] in) {
1381             Log.d(TAG, "Baz transpose2 " + Arrays.deepToString(in));
1382 
1383             String[][] out = new String[3][5];
1384             for (int i = 0; i < 3; ++i) {
1385                 for (int j = 0; j < 5; ++j) {
1386                     out[i][j] = in[j][i];
1387                 }
1388             }
1389 
1390             return out;
1391         }
1392 
someBoolMethod(boolean x)1393         public boolean someBoolMethod(boolean x) {
1394             Log.d(TAG, "Baz someBoolMethod(" + x + ")");
1395 
1396             return !x;
1397         }
1398 
someBoolArrayMethod(boolean[] x)1399         public boolean[] someBoolArrayMethod(boolean[] x) {
1400             Log.d(TAG, "Baz someBoolArrayMethod(" + Arrays.toString(x) + ")");
1401 
1402             boolean[] out = new boolean[4];
1403             out[0] = !x[0];
1404             out[1] = !x[1];
1405             out[2] = !x[2];
1406             out[3] = true;
1407 
1408             return out;
1409         }
1410 
someBoolVectorMethod(ArrayList<Boolean> x)1411         public ArrayList<Boolean> someBoolVectorMethod(ArrayList<Boolean> x) {
1412             Log.d(TAG, "Baz someBoolVectorMethod(" + x.toString() + ")");
1413 
1414             ArrayList<Boolean> out = new ArrayList<Boolean>();
1415             for (int i = 0; i < x.size(); ++i) {
1416                 out.add(!x.get(i));
1417             }
1418 
1419             return out;
1420         }
1421 
doThis(float param)1422         public void doThis(float param) {
1423             Log.d(TAG, "Baz doThis " + param);
1424         }
1425 
doThatAndReturnSomething(long param)1426         public int doThatAndReturnSomething(long param) {
1427             Log.d(TAG, "Baz doThatAndReturnSomething " + param);
1428             return 666;
1429         }
1430 
doQuiteABit(int a, long b, float c, double d)1431         public double doQuiteABit(int a, long b, float c, double d) {
1432             Log.d(TAG, "Baz doQuiteABit " + a + ", " + b + ", " + c + ", " + d);
1433             return 666.5;
1434         }
1435 
doSomethingElse(int[] param)1436         public int[] doSomethingElse(int[] param) {
1437             Log.d(TAG, "Baz doSomethingElse " + Arrays.toString(param));
1438 
1439             int[] something = new int[32];
1440             for (int i = 0; i < 15; ++i) {
1441                 something[i] = 2 * param[i];
1442                 something[15 + i] = param[i];
1443             }
1444             something[30] = 1;
1445             something[31] = 2;
1446 
1447             return something;
1448         }
1449 
doStuffAndReturnAString()1450         public String doStuffAndReturnAString() {
1451             Log.d(TAG, "doStuffAndReturnAString");
1452             return "Hello, world!";
1453         }
1454 
mapThisVector(ArrayList<Integer> param)1455         public ArrayList<Integer> mapThisVector(ArrayList<Integer> param) {
1456             Log.d(TAG, "mapThisVector " + param.toString());
1457 
1458             ArrayList<Integer> out = new ArrayList<Integer>();
1459 
1460             for (int i = 0; i < param.size(); ++i) {
1461                 out.add(2 * param.get(i));
1462             }
1463 
1464             return out;
1465         }
1466 
takeAMask(byte bf, byte first, IBase.MyMask second, byte third, takeAMaskCallback cb)1467         public void takeAMask(byte bf, byte first, IBase.MyMask second, byte third,
1468                 takeAMaskCallback cb) {
1469             cb.onValues(bf, (byte) (bf | first), (byte) (second.value & bf), (byte) (bf & third));
1470         }
1471 
testArrays(LotsOfPrimitiveArrays in)1472         public LotsOfPrimitiveArrays testArrays(LotsOfPrimitiveArrays in) {
1473             Log.d(TAG, "tesArrays " + in.toString());
1474             return in;
1475         }
1476 
testByteVecs(ArrayList<byte[]> in)1477         public ArrayList<byte[]> testByteVecs(ArrayList<byte[]> in) {
1478             return in;
1479         }
1480 
testBooleanVecs(ArrayList<boolean[]> in)1481         public ArrayList<boolean[]> testBooleanVecs(ArrayList<boolean[]> in) {
1482             return in;
1483         }
1484 
testDoubleVecs(ArrayList<double[]> in)1485         public ArrayList<double[]> testDoubleVecs(ArrayList<double[]> in) {
1486             return in;
1487         }
1488 
returnABitField()1489         public byte returnABitField() {
1490             return 0;
1491         }
1492 
size(int size)1493         public int size(int size) {
1494             return size;
1495         }
1496 
1497         @Override
getNestedStructs()1498         public ArrayList<NestedStruct> getNestedStructs() throws RemoteException {
1499             return new ArrayList<>();
1500         }
1501 
1502         class BazCallback extends IBazCallback.Stub {
heyItsMe(IBazCallback cb)1503             public void heyItsMe(IBazCallback cb) {
1504                 Log.d(TAG, "SERVER: heyItsMe");
1505             }
1506 
hey()1507             public void hey() {
1508                 Log.d(TAG, "SERVER: hey");
1509             }
1510         }
1511 
callMe(IBazCallback cb)1512         public void callMe(IBazCallback cb) throws RemoteException {
1513             Log.d(TAG, "callMe");
1514             cb.heyItsMe(new BazCallback());
1515         }
1516 
1517         private IBazCallback mStoredCallback;
callMeLater(IBazCallback cb)1518         public void callMeLater(IBazCallback cb) {
1519             mStoredCallback = cb;
1520         }
1521 
iAmFreeNow()1522         public void iAmFreeNow() throws RemoteException {
1523             if (mStoredCallback != null) {
1524                 mStoredCallback.hey();
1525             }
1526         }
1527 
dieNow()1528         public void dieNow() { System.exit(0); }
1529 
useAnEnum(byte zzz)1530         public byte useAnEnum(byte zzz) {
1531             Log.d(TAG, "useAnEnum " + zzz);
1532             return SomeEnum.quux;
1533         }
1534 
haveSomeStrings(String[] array)1535         public String[] haveSomeStrings(String[] array) {
1536             Log.d(TAG, "haveSomeStrings ["
1537                         + "\"" + array[0] + "\", "
1538                         + "\"" + array[1] + "\", "
1539                         + "\"" + array[2] + "\"]");
1540 
1541             String[] result = new String[2];
1542             result[0] = "Hello";
1543             result[1] = "World";
1544 
1545             return result;
1546         }
1547 
haveAStringVec(ArrayList<String> vector)1548         public ArrayList<String> haveAStringVec(ArrayList<String> vector) {
1549             Log.d(TAG, "haveAStringVec ["
1550                         + "\"" + vector.get(0) + "\", "
1551                         + "\"" + vector.get(1) + "\", "
1552                         + "\"" + vector.get(2) + "\"]");
1553 
1554             ArrayList<String> result = new ArrayList<String>();
1555             result.add("Hello");
1556             result.add("World");
1557 
1558             return result;
1559         }
1560 
repeatBitfieldVec(ArrayList<Byte> vector)1561         public ArrayList<Byte> repeatBitfieldVec(ArrayList<Byte> vector) { return vector; }
1562 
returnABunchOfStrings(returnABunchOfStringsCallback cb)1563         public void returnABunchOfStrings(returnABunchOfStringsCallback cb) {
1564             cb.onValues("Eins", "Zwei", "Drei");
1565         }
1566 
haveSomeStructWithInterface(StructWithInterface swi)1567         public StructWithInterface haveSomeStructWithInterface(StructWithInterface swi) {
1568             return swi;
1569         }
1570     }
1571 
1572     class SafeUnion extends ISafeUnion.Stub {
1573         @Override
newLargeSafeUnion()1574         public LargeSafeUnion newLargeSafeUnion() {
1575             Log.d(TAG, "SERVER: newLargeSafeUnion");
1576             return new LargeSafeUnion();
1577         }
1578 
1579         @Override
setA(LargeSafeUnion safeUnion, byte a)1580         public LargeSafeUnion setA(LargeSafeUnion safeUnion, byte a) {
1581             Log.d(TAG, "SERVER: setA(" + a + ")");
1582             safeUnion.a(a);
1583 
1584             return safeUnion;
1585         }
1586 
1587         @Override
setB(LargeSafeUnion safeUnion, short b)1588         public LargeSafeUnion setB(LargeSafeUnion safeUnion, short b) {
1589             Log.d(TAG, "SERVER: setB(" + b + ")");
1590             safeUnion.b(b);
1591 
1592             return safeUnion;
1593         }
1594 
1595         @Override
setC(LargeSafeUnion safeUnion, int c)1596         public LargeSafeUnion setC(LargeSafeUnion safeUnion, int c) {
1597             Log.d(TAG, "SERVER: setC(" + c + ")");
1598             safeUnion.c(c);
1599 
1600             return safeUnion;
1601         }
1602 
1603         @Override
setD(LargeSafeUnion safeUnion, long d)1604         public LargeSafeUnion setD(LargeSafeUnion safeUnion, long d) {
1605             Log.d(TAG, "SERVER: setD(" + d + ")");
1606             safeUnion.d(d);
1607 
1608             return safeUnion;
1609         }
1610 
1611         @Override
setE(LargeSafeUnion safeUnion, byte[ ] e)1612         public LargeSafeUnion setE(LargeSafeUnion safeUnion, byte[/* 13 */] e) {
1613             Log.d(TAG, "SERVER: setE(" + Arrays.toString(e) + ")");
1614             safeUnion.e(e);
1615 
1616             return safeUnion;
1617         }
1618 
1619         @Override
setF(LargeSafeUnion safeUnion, long[ ] f)1620         public LargeSafeUnion setF(LargeSafeUnion safeUnion, long[/* 5 */] f) {
1621             Log.d(TAG, "SERVER: setF(" + Arrays.toString(f) + ")");
1622             safeUnion.f(f);
1623 
1624             return safeUnion;
1625         }
1626 
1627         @Override
setG(LargeSafeUnion safeUnion, String g)1628         public LargeSafeUnion setG(LargeSafeUnion safeUnion, String g) {
1629             Log.d(TAG, "SERVER: setG(" + g + ")");
1630             safeUnion.g(g);
1631 
1632             return safeUnion;
1633         }
1634 
1635         @Override
setH(LargeSafeUnion safeUnion, ArrayList<Boolean> h)1636         public LargeSafeUnion setH(LargeSafeUnion safeUnion, ArrayList<Boolean> h) {
1637             Log.d(TAG, "SERVER: setH(" + h + ")");
1638             safeUnion.h(h);
1639 
1640             return safeUnion;
1641         }
1642 
1643         @Override
setI(LargeSafeUnion safeUnion, ArrayList<Long> i)1644         public LargeSafeUnion setI(LargeSafeUnion safeUnion, ArrayList<Long> i) {
1645             Log.d(TAG, "SERVER: setI(" + i + ")");
1646             safeUnion.i(i);
1647 
1648             return safeUnion;
1649         }
1650 
1651         @Override
setJ(LargeSafeUnion safeUnion, ISafeUnion.J j)1652         public LargeSafeUnion setJ(LargeSafeUnion safeUnion, ISafeUnion.J j) {
1653             Log.d(TAG, "SERVER: setJ(" + j + ")");
1654             safeUnion.j(j);
1655 
1656             return safeUnion;
1657         }
1658 
1659         @Override
setK(LargeSafeUnion safeUnion, LargeSafeUnion.K k)1660         public LargeSafeUnion setK(LargeSafeUnion safeUnion, LargeSafeUnion.K k) {
1661             Log.d(TAG, "SERVER: setK(" + k + ")");
1662             safeUnion.k(k);
1663 
1664             return safeUnion;
1665         }
1666 
1667         @Override
setL(LargeSafeUnion safeUnion, SmallSafeUnion l)1668         public LargeSafeUnion setL(LargeSafeUnion safeUnion, SmallSafeUnion l) {
1669             Log.d(TAG, "SERVER: setL(" + l + ")");
1670             safeUnion.l(l);
1671 
1672             return safeUnion;
1673         }
1674 
1675         @Override
setM(LargeSafeUnion safeUnion, byte m)1676         public LargeSafeUnion setM(LargeSafeUnion safeUnion, byte m) {
1677             Log.d(TAG, "SERVER: setM(" + m + ")");
1678             safeUnion.m(m);
1679 
1680             return safeUnion;
1681         }
1682 
1683         @Override
setN(LargeSafeUnion safeUnion, byte n)1684         public LargeSafeUnion setN(LargeSafeUnion safeUnion, byte n) {
1685             Log.d(TAG, "SERVER: setN(" + n + ")");
1686             safeUnion.n(n);
1687 
1688             return safeUnion;
1689         }
1690 
1691         @Override
newInterfaceTypeSafeUnion()1692         public InterfaceTypeSafeUnion newInterfaceTypeSafeUnion() {
1693             Log.d(TAG, "SERVER: newInterfaceTypeSafeUnion");
1694             return new InterfaceTypeSafeUnion();
1695         }
1696 
1697         @Override
setInterfaceA(InterfaceTypeSafeUnion safeUnion, int a)1698         public InterfaceTypeSafeUnion setInterfaceA(InterfaceTypeSafeUnion safeUnion, int a) {
1699             Log.d(TAG, "SERVER: setInterfaceA(" + a + ")");
1700             safeUnion.a(a);
1701 
1702             return safeUnion;
1703         }
1704 
1705         @Override
setInterfaceB( InterfaceTypeSafeUnion safeUnion, byte[ ] b)1706         public InterfaceTypeSafeUnion setInterfaceB(
1707             InterfaceTypeSafeUnion safeUnion, byte[/* 7 */] b) {
1708             Log.d(TAG, "SERVER: setInterfaceB(" + Arrays.toString(b) + ")");
1709             safeUnion.b(b);
1710 
1711             return safeUnion;
1712         }
1713 
1714         @Override
setInterfaceC( InterfaceTypeSafeUnion safeUnion, android.hidl.base.V1_0.IBase c)1715         public InterfaceTypeSafeUnion setInterfaceC(
1716                 InterfaceTypeSafeUnion safeUnion, android.hidl.base.V1_0.IBase c) {
1717             Log.d(TAG, "SERVER: setInterfaceC(" + c + ")");
1718             safeUnion.c(c);
1719 
1720             return safeUnion;
1721         }
1722 
1723         @Override
setInterfaceD(InterfaceTypeSafeUnion safeUnion, String d)1724         public InterfaceTypeSafeUnion setInterfaceD(InterfaceTypeSafeUnion safeUnion, String d) {
1725             Log.d(TAG, "SERVER: setInterfaceD(" + d + ")");
1726             safeUnion.d(d);
1727 
1728             return safeUnion;
1729         }
1730 
1731         @Override
setInterfaceE( InterfaceTypeSafeUnion safeUnion, ArrayList<String> e)1732         public InterfaceTypeSafeUnion setInterfaceE(
1733             InterfaceTypeSafeUnion safeUnion, ArrayList<String> e) {
1734             Log.d(TAG, "SERVER: setInterfaceE(" + e + ")");
1735             safeUnion.e(e);
1736 
1737             return safeUnion;
1738         }
1739 
1740         @Override
setInterfaceF( InterfaceTypeSafeUnion safeUnion, NativeHandle f)1741         public InterfaceTypeSafeUnion setInterfaceF(
1742             InterfaceTypeSafeUnion safeUnion, NativeHandle f) {
1743             Log.d(TAG, "SERVER: setInterfaceF(" + f + ")");
1744             safeUnion.f(f);
1745 
1746             return safeUnion;
1747         }
1748 
1749         @Override
setInterfaceG( InterfaceTypeSafeUnion safeUnion, ArrayList<NativeHandle> g)1750         public InterfaceTypeSafeUnion setInterfaceG(
1751             InterfaceTypeSafeUnion safeUnion, ArrayList<NativeHandle> g) {
1752             Log.d(TAG, "SERVER: setInterfaceG(" + g + ")");
1753             safeUnion.g(g);
1754 
1755             return safeUnion;
1756         }
1757 
1758         @Override
newHandleTypeSafeUnion()1759         public HandleTypeSafeUnion newHandleTypeSafeUnion() {
1760             Log.d(TAG, "SERVER: newHandleTypeSafeUnion");
1761             return new HandleTypeSafeUnion();
1762         }
1763 
1764         @Override
setHandleA(HandleTypeSafeUnion safeUnion, NativeHandle a)1765         public HandleTypeSafeUnion setHandleA(HandleTypeSafeUnion safeUnion, NativeHandle a) {
1766             Log.d(TAG, "SERVER: setHandleA(" + a + ")");
1767             safeUnion.a(a);
1768 
1769             return safeUnion;
1770         }
1771 
1772         @Override
setHandleB(HandleTypeSafeUnion safeUnion, NativeHandle[] b)1773         public HandleTypeSafeUnion setHandleB(HandleTypeSafeUnion safeUnion, NativeHandle[] b) {
1774             Log.d(TAG, "SERVER: setHandleB(" + Arrays.toString(b) + ")");
1775             safeUnion.b(b);
1776 
1777             return safeUnion;
1778         }
1779 
1780         @Override
setHandleC(HandleTypeSafeUnion safeUnion, ArrayList<NativeHandle> c)1781         public HandleTypeSafeUnion setHandleC(HandleTypeSafeUnion safeUnion,
1782                                               ArrayList<NativeHandle> c) {
1783             Log.d(TAG, "SERVER: setHandleC(" + c + ")");
1784             safeUnion.c(c);
1785 
1786             return safeUnion;
1787         }
1788     }
1789 
server()1790     private void server() throws RemoteException {
1791         HwBinder.configureRpcThreadpool(1, true);
1792 
1793         Baz baz = new Baz();
1794         baz.registerAsService("default");
1795 
1796         try {
1797             IBaz.getService("default");
1798             throw new RuntimeException("Java in-process enabled");
1799         } catch (NoSuchElementException e) {
1800             // as expected
1801         }
1802 
1803         SafeUnion safeunionInterface = new SafeUnion();
1804         safeunionInterface.registerAsService("default");
1805 
1806         HwBinder.joinRpcThreadpool();
1807     }
1808 }
1809