• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 android.hardware.tests.baz.V1_0.IBase;
20 import android.hardware.tests.baz.V1_0.IBaz;
21 import android.hardware.tests.baz.V1_0.IQuux;
22 import android.hardware.tests.baz.V1_0.IBaz.NestedStruct;
23 import android.hardware.tests.baz.V1_0.IBazCallback;
24 import android.os.HwBinder;
25 import android.os.RemoteException;
26 import android.os.HidlSupport;
27 import android.util.Log;
28 
29 import java.util.ArrayList;
30 import java.util.Arrays;
31 import java.util.NoSuchElementException;
32 
33 public final class HidlTestJava {
34     private static final String TAG = "HidlTestJava";
35 
main(String[] args)36     public static void main(String[] args) {
37         int exitCode = 1;
38         try {
39             exitCode = new HidlTestJava().run(args);
40         } catch (Exception e) {
41             e.printStackTrace();
42             Log.e(TAG, "Error ", e);
43         }
44         System.exit(exitCode);
45     }
46 
run(String[] args)47     public int run(String[] args) throws RemoteException {
48         if (args[0].equals("-c")) {
49             client();
50         } else if (args[0].equals("-s")) {
51             server();
52         } else {
53             Log.e(TAG, "Usage: HidlTestJava  -c(lient) | -s(erver)");
54             System.err.printf("Usage: HidlTestJava  -c(lient) | -s(erver)\n");
55             return 1;
56         }
57 
58         return 0;
59     }
60 
61     final class HidlDeathRecipient implements HwBinder.DeathRecipient {
62         final Object mLock = new Object();
63         boolean mCalled = false;
64         long mCookie = 0;
65 
66         @Override
serviceDied(long cookie)67         public void serviceDied(long cookie) {
68             synchronized (mLock) {
69                 mCalled = true;
70                 mCookie = cookie;
71                 mLock.notify();
72             }
73         }
74 
cookieMatches(long cookie)75         public boolean cookieMatches(long cookie) {
76             synchronized (mLock) {
77                 return mCookie == cookie;
78             }
79         }
80 
waitUntilServiceDied(long timeoutMillis)81         public boolean waitUntilServiceDied(long timeoutMillis) {
82             synchronized(mLock) {
83                 while (!mCalled) {
84                     try {
85                         mLock.wait(timeoutMillis);
86                     } catch (InterruptedException e) {
87                         continue; // Spin for another loop
88                     }
89                     break; // got notified or timeout hit
90                 }
91                 return mCalled;
92             }
93         }
94     };
95 
ExpectTrue(boolean x)96     private void ExpectTrue(boolean x) {
97         if (x) {
98             return;
99         }
100 
101         throw new RuntimeException();
102     }
103 
ExpectFalse(boolean x)104     private void ExpectFalse(boolean x) {
105         ExpectTrue(!x);
106     }
107 
Expect(String result, String s)108     private void Expect(String result, String s) {
109         if (result.equals(s)) {
110             return;
111         }
112 
113         System.err.printf("Expected '%s', got '%s'\n", s, result);
114         Log.e(TAG, "Expected '" + s + "', got '" + result + "'");
115         throw new RuntimeException();
116     }
117 
118     class BazCallback extends IBazCallback.Stub {
119         private boolean mCalled;
120 
BazCallback()121         public BazCallback() {
122             mCalled = false;
123         }
124 
wasCalled()125         boolean wasCalled() {
126             return mCalled;
127         }
128 
heyItsMe(IBazCallback cb)129         public void heyItsMe(IBazCallback cb) throws RemoteException {
130             mCalled = true;
131 
132             cb.heyItsMe(null);
133         }
134 
hey()135         public void hey() {
136             mCalled = true;
137         }
138     }
139 
numberToEnglish(int x)140     private String numberToEnglish(int x) {
141         final String[] kDigits = {
142             "zero",
143             "one",
144             "two",
145             "three",
146             "four",
147             "five",
148             "six",
149             "seven",
150             "eight",
151             "nine",
152         };
153 
154         if (x < 0) {
155             return "negative " + numberToEnglish(-x);
156         }
157 
158         if (x < 10) {
159             return kDigits[x];
160         }
161 
162         if (x <= 15) {
163             final String[] kSpecialTens = {
164                 "ten", "eleven", "twelve", "thirteen", "fourteen", "fifteen",
165             };
166 
167             return kSpecialTens[x - 10];
168         }
169 
170         if (x < 20) {
171             return kDigits[x % 10] + "teen";
172         }
173 
174         if (x < 100) {
175             final String[] kDecades = {
176                 "twenty", "thirty", "forty", "fifty", "sixty", "seventy",
177                 "eighty", "ninety",
178             };
179 
180             return kDecades[x / 10 - 2] + kDigits[x % 10];
181         }
182 
183         return "positively huge!";
184     }
185 
ExpectDeepEq(Object l, Object r)186     private void ExpectDeepEq(Object l, Object r) {
187         ExpectTrue(HidlSupport.deepEquals(l, r));
188         ExpectTrue(HidlSupport.deepHashCode(l) == HidlSupport.deepHashCode(r));
189     }
190 
ExpectDeepNe(Object l, Object r)191     private void ExpectDeepNe(Object l, Object r) {
192         ExpectTrue(!HidlSupport.deepEquals(l, r));
193     }
194 
client()195     private void client() throws RemoteException {
196 
197         ExpectDeepEq(null, null);
198         ExpectDeepNe(null, new String());
199         ExpectDeepNe(new String(), null);
200         ExpectDeepEq(new String(), new String());
201         ExpectDeepEq("hey", "hey");
202 
203         ExpectDeepEq(new int[]{1,2}, new int[]{1,2});
204         ExpectDeepNe(new int[]{1,2}, new int[]{1,3});
205         ExpectDeepNe(new int[]{1,2}, new int[]{1,2,3});
206         ExpectDeepEq(new int[][]{{1,2},{3,4}}, new int[][]{{1,2},{3,4}});
207         ExpectDeepNe(new int[][]{{1,2},{3,4}}, new int[][]{{1,2},{3,5}});
208         ExpectDeepNe(new int[][]{{1,2},{3,4}}, new int[][]{{1,2,3},{4,5,6}});
209         ExpectDeepNe(new int[][]{{1,2},{3,4}}, new int[][]{{1,2},{3,4,5}});
210 
211         ExpectDeepEq(new Integer[]{1,2}, new Integer[]{1,2});
212         ExpectDeepNe(new Integer[]{1,2}, new Integer[]{1,3});
213         ExpectDeepNe(new Integer[]{1,2}, new Integer[]{1,2,3});
214         ExpectDeepEq(new Integer[][]{{1,2},{3,4}}, new Integer[][]{{1,2},{3,4}});
215         ExpectDeepNe(new Integer[][]{{1,2},{3,4}}, new Integer[][]{{1,2},{3,5}});
216         ExpectDeepNe(new Integer[][]{{1,2},{3,4}}, new Integer[][]{{1,2,3},{4,5,6}});
217         ExpectDeepNe(new Integer[][]{{1,2},{3,4}}, new Integer[][]{{1,2},{3,4,5}});
218 
219         ExpectDeepEq(new ArrayList(Arrays.asList(1, 2)),
220                      new ArrayList(Arrays.asList(1, 2)));
221         ExpectDeepNe(new ArrayList(Arrays.asList(1, 2)),
222                      new ArrayList(Arrays.asList(1, 2, 3)));
223 
224         ExpectDeepEq(new ArrayList(Arrays.asList(new int[]{1,2}, new int[]{3,4})),
225                      new ArrayList(Arrays.asList(new int[]{1,2}, new int[]{3,4})));
226         ExpectDeepNe(new ArrayList(Arrays.asList(new int[]{1,2}, new int[]{3,4})),
227                      new ArrayList(Arrays.asList(new int[]{1,2}, new int[]{3,5})));
228 
229         ExpectDeepEq(new ArrayList(Arrays.asList(new Integer[]{1,2}, new Integer[]{3,4})),
230                      new ArrayList(Arrays.asList(new Integer[]{1,2}, new Integer[]{3,4})));
231         ExpectDeepNe(new ArrayList(Arrays.asList(new Integer[]{1,2}, new Integer[]{3,4})),
232                      new ArrayList(Arrays.asList(new Integer[]{1,2}, new Integer[]{3,5})));
233 
234         ExpectDeepEq(new ArrayList[]{new ArrayList(Arrays.asList(1,2)),
235                                      new ArrayList(Arrays.asList(3,4))},
236                      new ArrayList[]{new ArrayList(Arrays.asList(1,2)),
237                                      new ArrayList(Arrays.asList(3,4))});
238 
239         {
240             // Test proper exceptions are thrown
241             try {
242                 IBase proxy = IBase.getService("this-doesn't-exist");
243             } catch (Exception e) {
244                 ExpectTrue(e instanceof NoSuchElementException);
245             }
246         }
247 
248         {
249             // Test access through base interface binder.
250             IBase baseProxy = IBase.getService("baz");
251             baseProxy.someBaseMethod();
252 
253             IBaz bazProxy = IBaz.castFrom(baseProxy);
254             ExpectTrue(bazProxy != null);
255 
256             // IQuux is completely unrelated to IBase/IBaz, so the following
257             // should fail, i.e. return null.
258             IQuux quuxProxy = IQuux.castFrom(baseProxy);
259             ExpectTrue(quuxProxy == null);
260         }
261 
262         IBaz proxy = IBaz.getService("baz");
263         proxy.someBaseMethod();
264 
265         {
266             Expect(proxy.interfaceDescriptor(), IBaz.kInterfaceName);
267         }
268 
269         {
270             IBase.Foo foo = new IBase.Foo();
271             foo.x = 1;
272 
273             for (int i = 0; i < 5; ++i) {
274                 IBase.Foo.Bar bar = new IBase.Foo.Bar();
275                 bar.z = 1.0f + (float)i * 0.01f;
276                 bar.s = "Hello, world " + i;
277                 foo.aaa.add(bar);
278             }
279 
280             foo.y.z = 3.14f;
281             foo.y.s = "Lorem ipsum...";
282 
283             IBase.Foo result = proxy.someOtherBaseMethod(foo);
284             ExpectTrue(result.equals(foo));
285         }
286 
287         {
288             IBase.Foo[] inputArray = new IBase.Foo[2];
289 
290             IBase.Foo foo = new IBase.Foo();
291             foo.x = 1;
292 
293             for (int i = 0; i < 5; ++i) {
294                 IBase.Foo.Bar bar = new IBase.Foo.Bar();
295                 bar.z = 1.0f + (float)i * 0.01f;
296                 bar.s = "Hello, world " + i;
297                 foo.aaa.add(bar);
298             }
299 
300             foo.y.z = 3.14f;
301             foo.y.s = "Lorem ipsum...";
302 
303             inputArray[0] = foo;
304 
305             foo = new IBase.Foo();
306             foo.x = 2;
307 
308             for (int i = 0; i < 3; ++i) {
309                 IBase.Foo.Bar bar = new IBase.Foo.Bar();
310                 bar.z = 2.0f - (float)i * 0.01f;
311                 bar.s = "Lorem ipsum " + i;
312                 foo.aaa.add(bar);
313             }
314 
315             foo.y.z = 1.1414f;
316             foo.y.s = "Et tu brute?";
317 
318             inputArray[1] = foo;
319 
320             IBase.Foo[] expectedOutputArray = new IBase.Foo[2];
321             expectedOutputArray[0] = inputArray[1];
322             expectedOutputArray[1] = inputArray[0];
323 
324             IBase.Foo[] outputArray = proxy.someMethodWithFooArrays(inputArray);
325 
326             ExpectTrue(java.util.Objects.deepEquals(outputArray, expectedOutputArray));
327         }
328 
329         {
330             ArrayList<IBase.Foo> inputVec = new ArrayList<IBase.Foo>();
331 
332             IBase.Foo foo = new IBase.Foo();
333             foo.x = 1;
334 
335             for (int i = 0; i < 5; ++i) {
336                 IBase.Foo.Bar bar = new IBase.Foo.Bar();
337                 bar.z = 1.0f + (float)i * 0.01f;
338                 bar.s = "Hello, world " + i;
339                 foo.aaa.add(bar);
340             }
341 
342             foo.y.z = 3.14f;
343             foo.y.s = "Lorem ipsum...";
344 
345             inputVec.add(foo);
346 
347             foo = new IBase.Foo();
348             foo.x = 2;
349 
350             for (int i = 0; i < 3; ++i) {
351                 IBase.Foo.Bar bar = new IBase.Foo.Bar();
352                 bar.z = 2.0f - (float)i * 0.01f;
353                 bar.s = "Lorem ipsum " + i;
354                 foo.aaa.add(bar);
355             }
356 
357             foo.y.z = 1.1414f;
358             foo.y.s = "Et tu brute?";
359 
360             inputVec.add(foo);
361 
362             ArrayList<IBase.Foo> expectedOutputVec = new ArrayList<IBase.Foo>();
363             expectedOutputVec.add(inputVec.get(1));
364             expectedOutputVec.add(inputVec.get(0));
365 
366             ArrayList<IBase.Foo> outputVec =
367                 proxy.someMethodWithFooVectors(inputVec);
368 
369             ExpectTrue(java.util.Objects.deepEquals(outputVec, expectedOutputVec));
370         }
371 
372         {
373             IBase.VectorOfArray in = new IBase.VectorOfArray();
374 
375             int k = 0;
376             for (int i = 0; i < 3; ++i) {
377                 byte[] mac = new byte[6];
378                 for (int j = 0; j < 6; ++j, ++k) {
379                     mac[j] = (byte)k;
380                 }
381 
382                 in.addresses.add(mac);
383             }
384 
385             IBase.VectorOfArray expectedOut = new IBase.VectorOfArray();
386             int n = in.addresses.size();
387 
388             for (int i = 0; i < n; ++i) {
389                 expectedOut.addresses.add(in.addresses.get(n - 1 - i));
390             }
391 
392             IBase.VectorOfArray out = proxy.someMethodWithVectorOfArray(in);
393             ExpectTrue(out.equals(expectedOut));
394         }
395 
396         {
397             ArrayList<byte[]> in = new ArrayList<byte[]>();
398 
399             int k = 0;
400             for (int i = 0; i < 3; ++i) {
401                 byte[] mac = new byte[6];
402                 for (int j = 0; j < 6; ++j, ++k) {
403                     mac[j] = (byte)k;
404                 }
405 
406                 in.add(mac);
407             }
408 
409             ArrayList<byte[]> expectedOut = new ArrayList<byte[]>();
410 
411             int n = in.size();
412             for (int i = 0; i < n; ++i) {
413                 expectedOut.add(in.get(n - 1 - i));
414             }
415 
416             ArrayList<byte[]> out = proxy.someMethodTakingAVectorOfArray(in);
417 
418             ExpectTrue(out.size() == expectedOut.size());
419             for  (int i = 0; i < n; ++i) {
420                 ExpectTrue(java.util.Objects.deepEquals(out.get(i), expectedOut.get(i)));
421             }
422         }
423 
424         {
425             IBase.StringMatrix5x3 in = new IBase.StringMatrix5x3();
426             IBase.StringMatrix3x5 expectedOut = new IBase.StringMatrix3x5();
427 
428             for (int i = 0; i < 5; ++i) {
429                 for (int j = 0; j < 3; ++j) {
430                     in.s[i][j] = numberToEnglish(3 * i + j + 1);
431                     expectedOut.s[j][i] = in.s[i][j];
432                 }
433             }
434 
435             IBase.StringMatrix3x5 out = proxy.transpose(in);
436 
437             // [[1 2 3] [4 5 6] [7 8 9] [10 11 12] [13 14 15]]^T
438             // = [[1 4 7 10 13] [2 5 8 11 14] [3 6 9 12 15]]
439             ExpectTrue(out.equals(expectedOut));
440         }
441 
442         {
443             String[][] in = new String[5][3];
444             String[][] expectedOut = new String[3][5];
445             for (int i = 0; i < 5; ++i) {
446                 for (int j = 0; j < 3; ++j) {
447                     in[i][j] = numberToEnglish(3 * i + j + 1);
448                     expectedOut[j][i] = in[i][j];
449                 }
450             }
451 
452             String[][] out = proxy.transpose2(in);
453 
454             // [[1 2 3] [4 5 6] [7 8 9] [10 11 12] [13 14 15]]^T
455             // = [[1 4 7 10 13] [2 5 8 11 14] [3 6 9 12 15]]
456             ExpectTrue(java.util.Arrays.deepEquals(out, expectedOut));
457         }
458 
459         ExpectTrue(proxy.someBoolMethod(true) == false);
460 
461         {
462             boolean[] someBoolArray = new boolean[3];
463             someBoolArray[0] = true;
464             someBoolArray[1] = false;
465             someBoolArray[2] = true;
466 
467             boolean[] resultArray = proxy.someBoolArrayMethod(someBoolArray);
468             ExpectTrue(resultArray[0] == false);
469             ExpectTrue(resultArray[1] == true);
470             ExpectTrue(resultArray[2] == false);
471 
472             ArrayList<Boolean> someBoolVec = new ArrayList<Boolean>();
473             someBoolVec.add(true);
474             someBoolVec.add(false);
475             someBoolVec.add(true);
476 
477             ArrayList<Boolean> resultVec = proxy.someBoolVectorMethod(someBoolVec);
478             ExpectTrue(resultVec.get(0) == false);
479             ExpectTrue(resultVec.get(1) == true);
480             ExpectTrue(resultVec.get(2) == false);
481         }
482 
483         proxy.doThis(1.0f);
484 
485         ExpectTrue(proxy.doThatAndReturnSomething(1) == 666);
486         ExpectTrue(proxy.doQuiteABit(1, 2L, 3.0f, 4.0) == 666.5);
487 
488         {
489             int[] paramArray = new int[15];
490             int[] expectedOutArray = new int[32];
491             ArrayList<Integer> paramVec = new ArrayList<Integer>();
492             ArrayList<Integer> expectedOutVec = new ArrayList<Integer>();
493 
494             for (int i = 0; i < paramArray.length; ++i) {
495                 paramArray[i] = i;
496                 paramVec.add(i);
497 
498                 expectedOutArray[i] = 2 * i;
499                 expectedOutArray[15 + i] = i;
500 
501                 expectedOutVec.add(2 * i);
502             }
503 
504             expectedOutArray[30] = 1;
505             expectedOutArray[31] = 2;
506 
507 
508             int[] outArray = proxy.doSomethingElse(paramArray);
509             ExpectTrue(java.util.Objects.deepEquals(outArray, expectedOutArray));
510 
511             ArrayList<Integer> outVec = proxy.mapThisVector(paramVec);
512             java.util.Objects.equals(outVec, expectedOutVec);
513 
514         }
515 
516         Expect(proxy.doStuffAndReturnAString(), "Hello, world!");
517 
518         BazCallback cb = new BazCallback();
519         ExpectTrue(!cb.wasCalled());
520         proxy.callMe(cb);
521         ExpectTrue(cb.wasCalled());
522 
523         ExpectTrue(proxy.useAnEnum(IBaz.SomeEnum.goober) == -64);
524 
525         {
526             String[] stringArray = new String[3];
527             stringArray[0] = "one";
528             stringArray[1] = "two";
529             stringArray[2] = "three";
530 
531             String[] expectedOutArray = new String[2];
532             expectedOutArray[0] = "Hello";
533             expectedOutArray[1] = "World";
534 
535             String[] outArray = proxy.haveSomeStrings(stringArray);
536             ExpectTrue(java.util.Arrays.deepEquals(outArray, expectedOutArray));
537 
538             ArrayList<String> stringVec = new ArrayList<String>();
539             stringVec.add("one");
540             stringVec.add("two");
541             stringVec.add("three");
542 
543             ArrayList<String> expectedOutVec = new ArrayList<String>();
544             expectedOutVec.add("Hello");
545             expectedOutVec.add("World");
546 
547             ExpectTrue(expectedOutVec.equals(proxy.haveAStringVec(stringVec)));
548         }
549 
550         proxy.returnABunchOfStrings(
551                 new IBaz.returnABunchOfStringsCallback() {
552                     @Override
553                     public void onValues(String a, String b, String c) {
554                         Expect(a, "Eins");
555                         Expect(b, "Zwei");
556                         Expect(c, "Drei");
557                     }
558                 });
559 
560         proxy.returnABunchOfStrings((a,b,c) -> Expect(a + b + c, "EinsZweiDrei"));
561 
562         proxy.callMeLater(new BazCallback());
563         System.gc();
564         proxy.iAmFreeNow();
565 
566         {
567             IBaz.T t1 = new IBaz.T();
568             IBaz.T t2 = new IBaz.T();
569             for (int i = 0; i < 5; i++) {
570                 for (int j = 0; j < 3; j++) {
571                     t1.matrix5x3[i][j] = t2.matrix5x3[i][j] = (i + 1) * (j + 1);
572                 }
573             }
574             ExpectTrue(t1.equals(t2));
575             ExpectTrue(t1.hashCode() == t2.hashCode());
576             t2.matrix5x3[4][2] = -60;
577             ExpectTrue(!t1.equals(t2));
578         }
579 
580         ArrayList<NestedStruct> structs = proxy.getNestedStructs();
581         ExpectTrue(structs.size() == 5);
582         ExpectTrue(structs.get(1).matrices.size() == 6);
583 
584         {
585             IBaz.Everything e = new IBaz.Everything();
586             Expect(e.toString(),
587                 "{.number = 0, .anotherNumber = 0, .s = , " +
588                 ".vs = [], .multidimArray = [[null, null], [null, null]], " +
589                 ".sArray = [null, null, null], .anotherStruct = {.first = , .last = }, .bf = }");
590             e.s = "string!";
591             e.number = 127;
592             e.anotherNumber = 100;
593             e.vs.addAll(Arrays.asList("One", "Two", "Three"));
594             for (int i = 0; i < e.multidimArray.length; i++)
595                 for (int j = 0; j < e.multidimArray[i].length; j++)
596                     e.multidimArray[i][j] = Integer.toString(i) + Integer.toString(j);
597             e.bf = IBaz.BitField.VALL;
598             e.anotherStruct.first = "James";
599             e.anotherStruct.last = "Bond";
600             Expect(e.toString(),
601                 "{.number = 127, .anotherNumber = 100, .s = string!, " +
602                 ".vs = [One, Two, Three], .multidimArray = [[00, 01], [10, 11]], " +
603                 ".sArray = [null, null, null], .anotherStruct = {.first = James, .last = Bond}, " +
604                 ".bf = V0 | V1 | V2 | V3 | VALL}");
605             Expect(IBaz.BitField.toString(IBaz.BitField.VALL), "VALL");
606             Expect(IBaz.BitField.toString((byte)(IBaz.BitField.V0 | IBaz.BitField.V2)), "0x5");
607             Expect(IBaz.BitField.dumpBitfield(IBaz.BitField.VALL), "V0 | V1 | V2 | V3 | VALL");
608             Expect(IBaz.BitField.dumpBitfield((byte)(IBaz.BitField.V1 | IBaz.BitField.V3 | 0xF0)),
609                 "V1 | V3 | 0xf0");
610 
611             Expect(proxy.toString(), IBaz.kInterfaceName + "@Proxy");
612         }
613 
614         {
615             // Ensure that native parcel is cleared even if the corresponding
616             // Java object isn't GC'd.
617             ArrayList<Integer> data4K = new ArrayList<>(1024);
618             for (int i = 0; i < 1024; i++) {
619                 data4K.add(i);
620             }
621 
622             for (int i = 0; i < 1024; i++) {
623                 // If they are not properly cleaned up, these calls will put 4MB of data in
624                 // kernel binder buffer, and will fail.
625                 try {
626                     proxy.mapThisVector(data4K);
627                 } catch (RemoteException ex) {
628                     throw new RuntimeException("Failed at call #" + Integer.toString(i), ex);
629                 }
630             }
631         }
632 
633         // --- DEATH RECIPIENT TESTING ---
634         // This must always be done last, since it will kill the native server process
635         HidlDeathRecipient recipient1 = new HidlDeathRecipient();
636         HidlDeathRecipient recipient2 = new HidlDeathRecipient();
637 
638         final int cookie1 = 0x1481;
639         final int cookie2 = 0x1482;
640         ExpectTrue(proxy.linkToDeath(recipient1, cookie1));
641         ExpectTrue(proxy.linkToDeath(recipient2, cookie2));
642         ExpectTrue(proxy.unlinkToDeath(recipient2));
643         try {
644             proxy.dieNow();
645         } catch (RemoteException e) {
646             // Expected
647         }
648         ExpectTrue(recipient1.waitUntilServiceDied(2000 /*timeoutMillis*/));
649         ExpectTrue(!recipient2.waitUntilServiceDied(2000 /*timeoutMillis*/));
650         ExpectTrue(recipient1.cookieMatches(cookie1));
651         Log.d(TAG, "OK, exiting");
652 
653     }
654 
655     class Baz extends IBaz.Stub {
656         // from IBase
someBaseMethod()657         public void someBaseMethod() {
658             Log.d(TAG, "Baz someBaseMethod");
659         }
660 
someOtherBaseMethod(IBase.Foo foo)661         public IBase.Foo someOtherBaseMethod(IBase.Foo foo) {
662             Log.d(TAG, "Baz someOtherBaseMethod " + foo.toString());
663             return foo;
664         }
665 
someMethodWithFooArrays(IBase.Foo[] fooInput)666         public IBase.Foo[] someMethodWithFooArrays(IBase.Foo[] fooInput) {
667             Log.d(TAG, "Baz someMethodWithFooArrays " + fooInput.toString());
668 
669             IBase.Foo[] fooOutput = new IBase.Foo[2];
670             fooOutput[0] = fooInput[1];
671             fooOutput[1] = fooInput[0];
672 
673             return fooOutput;
674         }
675 
someMethodWithFooVectors( ArrayList<IBase.Foo> fooInput)676         public ArrayList<IBase.Foo> someMethodWithFooVectors(
677                 ArrayList<IBase.Foo> fooInput) {
678             Log.d(TAG, "Baz someMethodWithFooVectors " + fooInput.toString());
679 
680             ArrayList<IBase.Foo> fooOutput = new ArrayList<IBase.Foo>();
681             fooOutput.add(fooInput.get(1));
682             fooOutput.add(fooInput.get(0));
683 
684             return fooOutput;
685         }
686 
someMethodWithVectorOfArray( IBase.VectorOfArray in)687         public IBase.VectorOfArray someMethodWithVectorOfArray(
688                 IBase.VectorOfArray in) {
689             Log.d(TAG, "Baz someMethodWithVectorOfArray " + in.toString());
690 
691             IBase.VectorOfArray out = new IBase.VectorOfArray();
692             int n = in.addresses.size();
693             for (int i = 0; i < n; ++i) {
694                 out.addresses.add(in.addresses.get(n - i - 1));
695             }
696 
697             return out;
698         }
699 
someMethodTakingAVectorOfArray( ArrayList<byte[ ]> in)700         public ArrayList<byte[/* 6 */]> someMethodTakingAVectorOfArray(
701                 ArrayList<byte[/* 6 */]> in) {
702             Log.d(TAG, "Baz someMethodTakingAVectorOfArray");
703 
704             int n = in.size();
705             ArrayList<byte[]> out = new ArrayList<byte[]>();
706             for (int i = 0; i < n; ++i) {
707                 out.add(in.get(n - i - 1));
708             }
709 
710             return out;
711         }
712 
transpose(IBase.StringMatrix5x3 in)713         public IBase.StringMatrix3x5 transpose(IBase.StringMatrix5x3 in) {
714             Log.d(TAG, "Baz transpose " + in.toString());
715 
716             IBase.StringMatrix3x5 out = new IBase.StringMatrix3x5();
717             for (int i = 0; i < 3; ++i) {
718                 for (int j = 0; j < 5; ++j) {
719                     out.s[i][j] = in.s[j][i];
720                 }
721             }
722 
723             return out;
724         }
725 
transpose2(String[][] in)726         public String[][] transpose2(String[][] in) {
727             Log.d(TAG, "Baz transpose2 " + in.toString());
728 
729             String[][] out = new String[3][5];
730             for (int i = 0; i < 3; ++i) {
731                 for (int j = 0; j < 5; ++j) {
732                     out[i][j] = in[j][i];
733                 }
734             }
735 
736             return out;
737         }
738 
someBoolMethod(boolean x)739         public boolean someBoolMethod(boolean x) {
740             Log.d(TAG, "Baz someBoolMethod(" + x + ")");
741 
742             return !x;
743         }
744 
someBoolArrayMethod(boolean[] x)745         public boolean[] someBoolArrayMethod(boolean[] x) {
746             Log.d(TAG, "Baz someBoolArrayMethod("
747                     + x.toString() + ")");
748 
749             boolean[] out = new boolean[4];
750             out[0] = !x[0];
751             out[1] = !x[1];
752             out[2] = !x[2];
753             out[3] = true;
754 
755             return out;
756         }
757 
someBoolVectorMethod(ArrayList<Boolean> x)758         public ArrayList<Boolean> someBoolVectorMethod(ArrayList<Boolean> x) {
759             Log.d(TAG, "Baz someBoolVectorMethod(" + x.toString() + ")");
760 
761             ArrayList<Boolean> out = new ArrayList<Boolean>();
762             for (int i = 0; i < x.size(); ++i) {
763                 out.add(!x.get(i));
764             }
765 
766             return out;
767         }
768 
doThis(float param)769         public void doThis(float param) {
770             Log.d(TAG, "Baz doThis " + param);
771         }
772 
doThatAndReturnSomething(long param)773         public int doThatAndReturnSomething(long param) {
774             Log.d(TAG, "Baz doThatAndReturnSomething " + param);
775             return 666;
776         }
777 
doQuiteABit(int a, long b, float c, double d)778         public double doQuiteABit(int a, long b, float c, double d) {
779             Log.d(TAG, "Baz doQuiteABit " + a + ", " + b + ", " + c + ", " + d);
780             return 666.5;
781         }
782 
doSomethingElse(int[] param)783         public int[] doSomethingElse(int[] param) {
784             Log.d(TAG, "Baz doSomethingElse " + param.toString());
785 
786             int[] something = new int[32];
787             for (int i = 0; i < 15; ++i) {
788                 something[i] = 2 * param[i];
789                 something[15 + i] = param[i];
790             }
791             something[30] = 1;
792             something[31] = 2;
793 
794             return something;
795         }
796 
doStuffAndReturnAString()797         public String doStuffAndReturnAString() {
798             Log.d(TAG, "doStuffAndReturnAString");
799             return "Hello, world!";
800         }
801 
mapThisVector(ArrayList<Integer> param)802         public ArrayList<Integer> mapThisVector(ArrayList<Integer> param) {
803             Log.d(TAG, "mapThisVector " + param.toString());
804 
805             ArrayList<Integer> out = new ArrayList<Integer>();
806 
807             for (int i = 0; i < param.size(); ++i) {
808                 out.add(2 * param.get(i));
809             }
810 
811             return out;
812         }
813 
takeAMask(byte bf, byte first, IBase.MyMask second, byte third, takeAMaskCallback cb)814         public void takeAMask(byte bf, byte first, IBase.MyMask second, byte third,
815                 takeAMaskCallback cb) {
816             cb.onValues(bf, (byte)(bf | first),
817                     (byte)(second.value & bf), (byte)((bf | bf) & third));
818         }
819 
returnABitField()820         public byte returnABitField() {
821             return 0;
822         }
823 
size(int size)824         public int size(int size) {
825             return size;
826         }
827 
828         @Override
getNestedStructs()829         public ArrayList<NestedStruct> getNestedStructs() throws RemoteException {
830             return new ArrayList<>();
831         }
832 
833         class BazCallback extends IBazCallback.Stub {
heyItsMe(IBazCallback cb)834             public void heyItsMe(IBazCallback cb) {
835                 Log.d(TAG, "SERVER: heyItsMe");
836             }
837 
hey()838             public void hey() {
839                 Log.d(TAG, "SERVER: hey");
840             }
841         }
842 
callMe(IBazCallback cb)843         public void callMe(IBazCallback cb) throws RemoteException {
844             Log.d(TAG, "callMe");
845             cb.heyItsMe(new BazCallback());
846         }
847 
848         private IBazCallback mStoredCallback;
callMeLater(IBazCallback cb)849         public void callMeLater(IBazCallback cb) {
850             mStoredCallback = cb;
851         }
852 
iAmFreeNow()853         public void iAmFreeNow() throws RemoteException {
854             if (mStoredCallback != null) {
855                 mStoredCallback.hey();
856             }
857         }
858 
dieNow()859         public void dieNow() {
860             // Not tested in Java
861         }
862 
useAnEnum(byte zzz)863         public byte useAnEnum(byte zzz) {
864             Log.d(TAG, "useAnEnum " + zzz);
865             return SomeEnum.quux;
866         }
867 
haveSomeStrings(String[] array)868         public String[] haveSomeStrings(String[] array) {
869             Log.d(TAG, "haveSomeStrings ["
870                         + "\"" + array[0] + "\", "
871                         + "\"" + array[1] + "\", "
872                         + "\"" + array[2] + "\"]");
873 
874             String[] result = new String[2];
875             result[0] = "Hello";
876             result[1] = "World";
877 
878             return result;
879         }
880 
haveAStringVec(ArrayList<String> vector)881         public ArrayList<String> haveAStringVec(ArrayList<String> vector) {
882             Log.d(TAG, "haveAStringVec ["
883                         + "\"" + vector.get(0) + "\", "
884                         + "\"" + vector.get(1) + "\", "
885                         + "\"" + vector.get(2) + "\"]");
886 
887             ArrayList<String> result = new ArrayList<String>();
888             result.add("Hello");
889             result.add("World");
890 
891             return result;
892         }
893 
returnABunchOfStrings(returnABunchOfStringsCallback cb)894         public void returnABunchOfStrings(returnABunchOfStringsCallback cb) {
895             cb.onValues("Eins", "Zwei", "Drei");
896         }
897     }
898 
server()899     private void server() throws RemoteException {
900         HwBinder.configureRpcThreadpool(1, true);
901 
902         Baz baz = new Baz();
903         baz.registerAsService("baz");
904 
905         HwBinder.joinRpcThreadpool();
906     }
907 }
908