Edit SF and WM config from winscope. am: 5284e5a483

Original change: https://googleplex-android-review.googlesource.com/c/platform/development/+/16047809

Change-Id: I2b50e786984ca93f5d5803522f9bf49b41caf30a
This commit is contained in:
Priyanka
2021-10-13 16:46:53 +00:00
committed by Automerger Merge Worker
2 changed files with 207 additions and 18 deletions

View File

@@ -203,6 +203,52 @@ class SurfaceFlingerTraceConfig:
def command(self) -> str:
return f'su root service call SurfaceFlinger 1033 i32 {self.flags}'
class SurfaceFlingerTraceSelectedConfig:
"""Handles optional selected configuration for surfaceflinger traces.
"""
def __init__(self) -> None:
# defaults set for all configs
self.selectedConfigs = {
"sfbuffersize": "16000"
}
def add(self, configType, configValue) -> None:
self.selectedConfigs[configType] = configValue
def is_valid(self, configType) -> bool:
return configType in CONFIG_SF_SELECTION
def setBufferSize(self) -> str:
return f'su root service call SurfaceFlinger 1029 i32 {self.selectedConfigs["sfbuffersize"]}'
class WindowManagerTraceSelectedConfig:
"""Handles optional selected configuration for windowmanager traces.
"""
def __init__(self) -> None:
# defaults set for all configs
self.selectedConfigs = {
"wmbuffersize": "16000",
"tracinglevel": "all",
"tracingtype": "frame",
}
def add(self, configType, configValue) -> None:
self.selectedConfigs[configType] = configValue
def is_valid(self, configType) -> bool:
return configType in CONFIG_WM_SELECTION
def setBufferSize(self) -> str:
return f'su root cmd window tracing size {self.selectedConfigs["wmbuffersize"]}'
def setTracingLevel(self) -> str:
return f'su root cmd window tracing level {self.selectedConfigs["tracinglevel"]}'
def setTracingType(self) -> str:
return f'su root cmd window tracing {self.selectedConfigs["tracingtype"]}'
CONFIG_FLAG = {
"composition": 1 << 2,
@@ -210,6 +256,17 @@ CONFIG_FLAG = {
"hwc": 1 << 4
}
#Keep up to date with options in DataAdb.vue
CONFIG_SF_SELECTION = [
"sfbuffersize",
]
#Keep up to date with options in DataAdb.vue
CONFIG_WM_SELECTION = [
"wmbuffersize",
"tracingtype",
"tracinglevel",
]
class DumpTarget:
"""Defines a single parameter to trace.
@@ -610,6 +667,18 @@ class EndTrace(DeviceRequestEndpoint):
"utf-8"))
def execute_command(server, device_id, shell, configType, configValue):
process = subprocess.Popen(shell, stdout=subprocess.PIPE, stderr=subprocess.PIPE,
stdin=subprocess.PIPE, start_new_session=True)
log.debug(f"Changing trace config on device {device_id} {configType}:{configValue}")
out, err = process.communicate(configValue.encode('utf-8'))
if process.returncode != 0:
raise AdbError(
f"Error executing command:\n {configValue}\n\n### OUTPUT ###{out.decode('utf-8')}\n{err.decode('utf-8')}")
log.debug(f"Changing trace config finished on device {device_id}")
server.respond(HTTPStatus.OK, b'', "text/plain")
class ConfigTrace(DeviceRequestEndpoint):
def process_with_device(self, server, path, device_id):
try:
@@ -630,15 +699,50 @@ class ConfigTrace(DeviceRequestEndpoint):
command = config.command()
shell = ['adb', '-s', device_id, 'shell']
log.debug(f"Starting shell {' '.join(shell)}")
process = subprocess.Popen(shell, stdout=subprocess.PIPE, stderr=subprocess.PIPE,
stdin=subprocess.PIPE, start_new_session=True)
log.debug(f"Changing trace config on device {device_id} cmd:{command}")
out, err = process.communicate(command.encode('utf-8'))
if process.returncode != 0:
raise AdbError(
f"Error executing command:\n {command}\n\n### OUTPUT ###{out.decode('utf-8')}\n{err.decode('utf-8')}")
log.debug(f"Changing trace config finished on device {device_id}")
server.respond(HTTPStatus.OK, b'', "text/plain")
execute_command(server, device_id, shell, "sf buffer size", command)
def add_selected_request_to_config(self, server, device_id, config):
try:
requested_configs = self.get_request(server)
for requested_config in requested_configs:
if config.is_valid(requested_config):
config.add(requested_config, requested_configs[requested_config])
else:
raise BadRequest(
f"Unsupported config {requested_config}\n")
except KeyError as err:
raise BadRequest("Unsupported trace target\n" + str(err))
if device_id in TRACE_THREADS:
BadRequest(f"Trace in progress for {device_id}")
if not check_root(device_id):
raise AdbError(
f"Unable to acquire root privileges on the device - check the output of 'adb -s {device_id} shell su root id'")
return config
class SurfaceFlingerSelectedConfigTrace(DeviceRequestEndpoint):
def process_with_device(self, server, path, device_id):
config = SurfaceFlingerTraceSelectedConfig()
config = add_selected_request_to_config(self, server, device_id, config)
setBufferSize = config.setBufferSize()
shell = ['adb', '-s', device_id, 'shell']
log.debug(f"Starting shell {' '.join(shell)}")
execute_command(server, device_id, shell, "sf buffer size", setBufferSize)
class WindowManagerSelectedConfigTrace(DeviceRequestEndpoint):
def process_with_device(self, server, path, device_id):
config = WindowManagerTraceSelectedConfig()
config = add_selected_request_to_config(self, server, device_id, config)
setBufferSize = config.setBufferSize()
setTracingType = config.setTracingType()
setTracingLevel = config.setTracingLevel()
shell = ['adb', '-s', device_id, 'shell']
log.debug(f"Starting shell {' '.join(shell)}")
execute_command(server, device_id, shell, "wm buffer size", setBufferSize)
execute_command(server, device_id, shell, "tracing type", setTracingType)
execute_command(server, device_id, shell, "tracing level", setTracingLevel)
class StatusEndpoint(DeviceRequestEndpoint):
@@ -691,6 +795,10 @@ class ADBWinscopeProxy(BaseHTTPRequestHandler):
self.router.register_endpoint(RequestType.POST, "dump", DumpEndpoint())
self.router.register_endpoint(
RequestType.POST, "configtrace", ConfigTrace())
self.router.register_endpoint(
RequestType.POST, "selectedsfconfigtrace", SurfaceFlingerSelectedConfigTrace())
self.router.register_endpoint(
RequestType.POST, "selectedwmconfigtrace", WindowManagerSelectedConfigTrace())
super().__init__(request, client_address, server)
def respond(self, code: int, data: bytes, mime: str) -> None:

View File

@@ -86,10 +86,29 @@
<div class="selection">
<md-checkbox class="md-primary" v-for="traceKey in Object.keys(TRACES)" :key="traceKey" v-model="adbStore[traceKey]">{{TRACES[traceKey].name}}</md-checkbox>
</div>
<div class="trace-config" v-for="traceKey in Object.keys(TRACE_CONFIG)" :key="traceKey">
<h4>{{TRACES[traceKey].name}} config</h4>
<div class="trace-config">
<h4>Surface Flinger config</h4>
<div class="selection">
<md-checkbox class="md-primary" v-for="config in TRACE_CONFIG[traceKey]" :key="config" v-model="adbStore[config]">{{config}}</md-checkbox>
<md-checkbox class="md-primary" v-for="config in TRACE_CONFIG['layers_trace']" :key="config" v-model="adbStore[config]">{{config}}</md-checkbox>
<div class="selection">
<md-field class="config-selection" v-for="selectConfig in Object.keys(SF_SELECTED_CONFIG)" :key="selectConfig">
<md-select v-model="SF_SELECTED_CONFIG_VALUES[selectConfig]" :placeholder="selectConfig">
<md-option value="">{{selectConfig}}</md-option>
<md-option v-for="option in SF_SELECTED_CONFIG[selectConfig]" :key="option" :value="option">{{ option }}</md-option>
</md-select>
</md-field>
</div>
</div>
</div>
<div class="trace-config">
<h4>Window Manager config</h4>
<div class="selection">
<md-field class="config-selection" v-for="selectConfig in Object.keys(WM_SELECTED_CONFIG)" :key="selectConfig">
<md-select v-model="WM_SELECTED_CONFIG_VALUES[selectConfig]" :placeholder="selectConfig">
<md-option value="">{{selectConfig}}</md-option>
<md-option v-for="option in WM_SELECTED_CONFIG[selectConfig]" :key="option" :value="option">{{ option }}</md-option>
</md-select>
</md-field>
</div>
</div>
<md-button class="md-primary trace-btn" @click="startTrace">Start trace</md-button>
@@ -149,6 +168,8 @@ const PROXY_ENDPOINTS = {
START_TRACE: '/start/',
END_TRACE: '/end/',
CONFIG_TRACE: '/configtrace/',
SELECTED_WM_CONFIG_TRACE: '/selectedwmconfigtrace/',
SELECTED_SF_CONFIG_TRACE: '/selectedsfconfigtrace/',
DUMP: '/dump/',
FETCH: '/fetch/',
STATUS: '/status/',
@@ -192,6 +213,33 @@ const TRACE_CONFIG = {
],
};
const SF_SELECTED_CONFIG = {
'sfbuffersize': [
'4000',
'8000',
'16000',
'32000',
],
};
const WM_SELECTED_CONFIG = {
'wmbuffersize': [
'4000',
'8000',
'16000',
'32000',
],
'tracingtype': [
'frame',
'transaction',
],
'tracinglevel': [
'all',
'trim',
'critical',
],
};
const DUMPS = {
'window_dump': {
name: 'Window Manager',
@@ -228,6 +276,10 @@ export default {
STATES,
TRACES,
TRACE_CONFIG,
SF_SELECTED_CONFIG,
WM_SELECTED_CONFIG,
SF_SELECTED_CONFIG_VALUES: {},
WM_SELECTED_CONFIG_VALUES: {},
DUMPS,
FILE_DECODERS,
WINSCOPE_PROXY_VERSION,
@@ -292,7 +344,7 @@ export default {
this.keep_alive_worker = null;
return;
}
this.callProxy('GET', PROXY_ENDPOINTS.STATUS + this.deviceId() + '/', this, function(request, view) {
this.callProxy('GET', `${PROXY_ENDPOINTS.STATUS}${this.deviceId()}/`, this, function(request, view) {
if (request.responseText !== 'True') {
view.endTrace();
} else if (view.keep_alive_worker === null) {
@@ -303,16 +355,21 @@ export default {
startTrace() {
const requested = this.toTrace();
const requestedConfig = this.toTraceConfig();
const requestedSelectedSfConfig = this.toSelectedSfTraceConfig();
const requestedSelectedWmConfig = this.toSelectedWmTraceConfig();
if (requested.length < 1) {
this.errorText = 'No targets selected';
this.status = STATES.ERROR;
this.newEventOccurred("No targets selected");
return;
}
this.newEventOccurred("Start Trace");
this.callProxy('POST', PROXY_ENDPOINTS.CONFIG_TRACE + this.deviceId() + '/', this, null, null, requestedConfig);
this.callProxy('POST', `${PROXY_ENDPOINTS.CONFIG_TRACE}${this.deviceId()}/`, this, null, null, requestedConfig);
this.callProxy('POST', `${PROXY_ENDPOINTS.SELECTED_SF_CONFIG_TRACE}${this.deviceId()}/`, this, null, null, requestedSelectedSfConfig);
this.callProxy('POST', `${PROXY_ENDPOINTS.SELECTED_WM_CONFIG_TRACE}${this.deviceId()}/`, this, null, null, requestedSelectedWmConfig);
this.status = STATES.END_TRACE;
this.callProxy('POST', PROXY_ENDPOINTS.START_TRACE + this.deviceId() + '/', this, function(request, view) {
this.callProxy('POST', `${PROXY_ENDPOINTS.START_TRACE}${this.deviceId()}/`, this, function(request, view) {
view.keepAliveTrace();
}, null, requested);
},
@@ -326,19 +383,19 @@ export default {
return;
}
this.status = STATES.LOAD_DATA;
this.callProxy('POST', PROXY_ENDPOINTS.DUMP + this.deviceId() + '/', this, function(request, view) {
this.callProxy('POST', `${PROXY_ENDPOINTS.DUMP}${this.deviceId()}/`, this, function(request, view) {
view.loadFile(requested, 0);
}, null, requested);
},
endTrace() {
this.status = STATES.LOAD_DATA;
this.callProxy('POST', PROXY_ENDPOINTS.END_TRACE + this.deviceId() + '/', this, function(request, view) {
this.callProxy('POST', `${PROXY_ENDPOINTS.END_TRACE}${this.deviceId()}/`, this, function(request, view) {
view.loadFile(view.toTrace(), 0);
});
this.newEventOccurred("Ended Trace");
},
loadFile(files, idx) {
this.callProxy('GET', PROXY_ENDPOINTS.FETCH + this.deviceId() + '/' + files[idx] + '/', this, function(request, view) {
this.callProxy('GET', `${PROXY_ENDPOINTS.FETCH}${this.deviceId()}/${files[idx]}/`, this, function(request, view) {
try {
const enc = new TextDecoder('utf-8');
const resp = enc.decode(request.response);
@@ -380,6 +437,24 @@ export default {
.flatMap((file) => TRACE_CONFIG[file])
.filter((config) => this.adbStore[config]);
},
toSelectedSfTraceConfig() {
const requestedSelectedConfig = {};
for (const config in this.SF_SELECTED_CONFIG_VALUES) {
if (this.SF_SELECTED_CONFIG_VALUES[config] !== "") {
requestedSelectedConfig[config] = this.SF_SELECTED_CONFIG_VALUES[config];
}
}
return requestedSelectedConfig;
},
toSelectedWmTraceConfig() {
const requestedSelectedConfig = {};
for (const config in this.WM_SELECTED_CONFIG_VALUES) {
if (this.WM_SELECTED_CONFIG_VALUES[config] !== "") {
requestedSelectedConfig[config] = this.WM_SELECTED_CONFIG_VALUES[config];
}
}
return requestedSelectedConfig;
},
toDump() {
return Object.keys(DUMPS)
.filter((dumpKey) => this.adbStore[dumpKey]);
@@ -459,6 +534,12 @@ export default {
</script>
<style scoped>
.config-selection {
width: 150px;
display: inline-flex;
margin-left: 5px;
margin-right: 5px;
}
.device-choice {
display: inline-flex;
}