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.server.wm; 18 19 import android.graphics.Rect; 20 import android.graphics.Region; 21 import android.os.IBinder; 22 import android.os.Parcel; 23 import android.util.Slog; 24 import android.view.SurfaceControl; 25 26 import java.io.FileDescriptor; 27 import java.io.FileOutputStream; 28 import java.io.DataOutputStream; 29 30 // A surface control subclass which logs events to a FD in binary format. 31 // This can be used in our CTS tests to enable a pattern similar to mocking 32 // the surface control. 33 // 34 // See cts/hostsidetests/../../SurfaceTraceReceiver.java for parsing side. 35 class RemoteSurfaceTrace extends SurfaceControl { 36 static final String TAG = "RemoteSurfaceTrace"; 37 38 final FileDescriptor mWriteFd; 39 final DataOutputStream mOut; 40 41 final WindowManagerService mService; 42 final WindowState mWindow; 43 RemoteSurfaceTrace(FileDescriptor fd, SurfaceControl wrapped, WindowState window)44 RemoteSurfaceTrace(FileDescriptor fd, SurfaceControl wrapped, WindowState window) { 45 super(wrapped); 46 47 mWriteFd = fd; 48 mOut = new DataOutputStream(new FileOutputStream(fd, false)); 49 50 mWindow = window; 51 mService = mWindow.mService; 52 } 53 54 @Override setAlpha(float alpha)55 public void setAlpha(float alpha) { 56 writeFloatEvent("Alpha", alpha); 57 super.setAlpha(alpha); 58 } 59 60 @Override setLayer(int zorder)61 public void setLayer(int zorder) { 62 writeIntEvent("Layer", zorder); 63 super.setLayer(zorder); 64 } 65 66 @Override setPosition(float x, float y)67 public void setPosition(float x, float y) { 68 writeFloatEvent("Position", x, y); 69 super.setPosition(x, y); 70 } 71 72 @Override setGeometryAppliesWithResize()73 public void setGeometryAppliesWithResize() { 74 writeEvent("GeometryAppliesWithResize"); 75 super.setGeometryAppliesWithResize(); 76 } 77 78 @Override setSize(int w, int h)79 public void setSize(int w, int h) { 80 writeIntEvent("Size", w, h); 81 super.setSize(w, h); 82 } 83 84 @Override setWindowCrop(Rect crop)85 public void setWindowCrop(Rect crop) { 86 writeRectEvent("Crop", crop); 87 super.setWindowCrop(crop); 88 } 89 90 @Override setFinalCrop(Rect crop)91 public void setFinalCrop(Rect crop) { 92 writeRectEvent("FinalCrop", crop); 93 super.setFinalCrop(crop); 94 } 95 96 @Override setLayerStack(int layerStack)97 public void setLayerStack(int layerStack) { 98 writeIntEvent("LayerStack", layerStack); 99 super.setLayerStack(layerStack); 100 } 101 102 @Override setMatrix(float dsdx, float dtdx, float dsdy, float dtdy)103 public void setMatrix(float dsdx, float dtdx, float dsdy, float dtdy) { 104 writeFloatEvent("Matrix", dsdx, dtdx, dsdy, dtdy); 105 super.setMatrix(dsdx, dtdx, dsdy, dtdy); 106 } 107 108 @Override hide()109 public void hide() { 110 writeEvent("Hide"); 111 super.hide(); 112 } 113 114 @Override show()115 public void show() { 116 writeEvent("Show"); 117 super.show(); 118 } 119 writeEvent(String tag)120 private void writeEvent(String tag) { 121 try { 122 mOut.writeUTF(tag); 123 mOut.writeUTF(mWindow.getWindowTag().toString()); 124 writeSigil(); 125 } catch (Exception e) { 126 RemoteEventTrace.logException(e); 127 mService.disableSurfaceTrace(); 128 } 129 } 130 writeIntEvent(String tag, int... values)131 private void writeIntEvent(String tag, int... values) { 132 try { 133 mOut.writeUTF(tag); 134 mOut.writeUTF(mWindow.getWindowTag().toString()); 135 for (int value: values) { 136 mOut.writeInt(value); 137 } 138 writeSigil(); 139 } catch (Exception e) { 140 RemoteEventTrace.logException(e); 141 mService.disableSurfaceTrace(); 142 } 143 } 144 writeFloatEvent(String tag, float... values)145 private void writeFloatEvent(String tag, float... values) { 146 try { 147 mOut.writeUTF(tag); 148 mOut.writeUTF(mWindow.getWindowTag().toString()); 149 for (float value: values) { 150 mOut.writeFloat(value); 151 } 152 writeSigil(); 153 } catch (Exception e) { 154 RemoteEventTrace.logException(e); 155 mService.disableSurfaceTrace(); 156 } 157 } 158 writeRectEvent(String tag, Rect value)159 private void writeRectEvent(String tag, Rect value) { 160 writeFloatEvent(tag, value.left, value.top, value.right, value.bottom); 161 } 162 writeSigil()163 private void writeSigil() throws Exception { 164 mOut.write(RemoteEventTrace.sigil, 0, 4); 165 } 166 } 167