Remove legacy JSC profiler

Reviewed By: bnham

Differential Revision: D5433406

fbshipit-source-id: 8cbea8b9b46a0d9f29c57a5bcf605e6bb61ed8a7
This commit is contained in:
Pieter De Baets 2017-07-20 04:04:37 -07:00 committed by Facebook Github Bot
parent bf752014a9
commit ed3c018ee4
33 changed files with 0 additions and 1833 deletions

View File

@ -1,13 +0,0 @@
// Copyright 2004-present Facebook. All Rights Reserved.
#pragma once
#import "JSContextRef.h"
extern "C" {
void nativeProfilerEnableBytecode(void);
void nativeProfilerStart(JSContextRef ctx, const char *title);
void nativeProfilerEnd(JSContextRef ctx, const char *title, const char *filename);
}

View File

@ -1,311 +0,0 @@
#include "JSCLegacyProfiler.h"
#include "APICast.h"
#include "LegacyProfiler.h"
#include "OpaqueJSString.h"
#include "JSProfilerPrivate.h"
#include "JSStringRef.h"
#include "String.h"
#include "Options.h"
enum json_gen_status {
json_gen_status_ok = 0,
json_gen_status_error = 1,
};
enum json_entry {
json_entry_key,
json_entry_value,
};
namespace {
struct json_state {
FILE *fileOut;
bool hasFirst;
};
}
typedef json_state *json_gen;
static void json_escaped_cstring_printf(json_gen gen, const char *str) {
const char *cursor = str;
fputc('"', gen->fileOut);
while (*cursor) {
const char *escape = nullptr;
switch (*cursor) {
case '"':
escape = "\\\"";
break;
case '\b':
escape = "\\b";
break;
case '\f':
escape = "\\f";
break;
case '\n':
escape = "\\n";
break;
case '\r':
escape = "\\r";
break;
case '\t':
escape = "\\t";
break;
case '\\':
escape = "\\\\";
break;
default:
break;
}
if (escape != nullptr) {
fwrite(escape, 1, strlen(escape), gen->fileOut);
} else {
fputc(*cursor, gen->fileOut);
}
cursor++;
}
fputc('"', gen->fileOut);
}
static json_gen_status json_gen_key_cstring(json_gen gen, const char *buffer) {
if (gen->fileOut == nullptr) {
return json_gen_status_error;
}
if (gen->hasFirst) {
fprintf(gen->fileOut, ",");
}
gen->hasFirst = true;
json_escaped_cstring_printf(gen, buffer);
return json_gen_status_ok;
}
static json_gen_status json_gen_map_open(json_gen gen, json_entry entryType) {
if (gen->fileOut == nullptr) {
return json_gen_status_error;
}
if (entryType == json_entry_value) {
fprintf(gen->fileOut, ":");
} else if (entryType == json_entry_key) {
if (gen->hasFirst) {
fprintf(gen->fileOut, ",");
}
}
fprintf(gen->fileOut, "{");
gen->hasFirst = false;
return json_gen_status_ok;
}
static json_gen_status json_gen_map_close(json_gen gen) {
if (gen->fileOut == nullptr) {
return json_gen_status_error;
}
fprintf(gen->fileOut, "}");
gen->hasFirst = true;
return json_gen_status_ok;
}
static json_gen_status json_gen_array_open(json_gen gen, json_entry entryType) {
if (gen->fileOut == nullptr) {
return json_gen_status_error;
}
if (entryType == json_entry_value) {
fprintf(gen->fileOut, ":");
} else if (entryType == json_entry_key) {
if (gen->hasFirst) {
fprintf(gen->fileOut, ",");
}
}
fprintf(gen->fileOut, "[");
gen->hasFirst = false;
return json_gen_status_ok;
}
static json_gen_status json_gen_array_close(json_gen gen) {
if (gen->fileOut == nullptr) {
return json_gen_status_error;
}
fprintf(gen->fileOut, "]");
gen->hasFirst = true;
return json_gen_status_ok;
}
static json_gen_status json_gen_keyvalue_cstring(json_gen gen, const char *key, const char *value) {
if (gen->fileOut == nullptr) {
return json_gen_status_error;
}
if (gen->hasFirst) {
fprintf(gen->fileOut, ",");
}
gen->hasFirst = true;
fprintf(gen->fileOut, "\"%s\" : ", key);
json_escaped_cstring_printf(gen, value);
return json_gen_status_ok;
}
static json_gen_status json_gen_keyvalue_integer(json_gen gen, const char *key, int value) {
if (gen->fileOut == nullptr) {
return json_gen_status_error;
}
if (gen->hasFirst) {
fprintf(gen->fileOut, ",");
}
gen->hasFirst = true;
fprintf(gen->fileOut, "\"%s\": %d", key, value);
return json_gen_status_ok;
}
static json_gen_status json_gen_keyvalue_double(json_gen gen, const char *key, double value) {
if (gen->fileOut == nullptr) {
return json_gen_status_error;
}
if (gen->hasFirst) {
fprintf(gen->fileOut, ",");
}
gen->hasFirst = true;
fprintf(gen->fileOut, "\"%s\": %.20g", key, value);
return json_gen_status_ok;
}
static json_gen json_gen_alloc(const char *fileName) {
json_gen gen = (json_gen)malloc(sizeof(json_state));
memset(gen, 0, sizeof(json_state));
gen->fileOut = fopen(fileName, "wb");
return gen;
}
static void json_gen_free(json_gen gen) {
if (gen->fileOut) {
fclose(gen->fileOut);
}
free(gen);
}
#define GEN_AND_CHECK(expr) \
do { \
json_gen_status GEN_AND_CHECK_status = (expr); \
if (GEN_AND_CHECK_status != json_gen_status_ok) { \
return GEN_AND_CHECK_status; \
} \
} while (false)
static json_gen_status append_children_array_json(json_gen gen, const JSC::ProfileNode *node);
static json_gen_status append_node_json(json_gen gen, const JSC::ProfileNode *node);
static json_gen_status append_root_json(json_gen gen, const JSC::Profile *profile) {
GEN_AND_CHECK(json_gen_map_open(gen, json_entry_key));
GEN_AND_CHECK(json_gen_key_cstring(gen, "rootNodes"));
#if IOS8
GEN_AND_CHECK(append_children_array_json(gen, profile->head()));
#else
GEN_AND_CHECK(append_children_array_json(gen, profile->rootNode()));
#endif
GEN_AND_CHECK(json_gen_map_close(gen));
return json_gen_status_ok;
}
static json_gen_status append_children_array_json(json_gen gen, const JSC::ProfileNode *node) {
GEN_AND_CHECK(json_gen_array_open(gen, json_entry_value));
for (RefPtr<JSC::ProfileNode> child : node->children()) {
GEN_AND_CHECK(append_node_json(gen, child.get()));
}
GEN_AND_CHECK(json_gen_array_close(gen));
return json_gen_status_ok;
}
static json_gen_status append_node_json(json_gen gen, const JSC::ProfileNode *node) {
GEN_AND_CHECK(json_gen_map_open(gen, json_entry_key));
GEN_AND_CHECK(json_gen_keyvalue_integer(gen, "id", node->id()));
if (!node->functionName().isEmpty()) {
GEN_AND_CHECK(json_gen_keyvalue_cstring(gen, "functionName", node->functionName().utf8().data()));
}
if (!node->url().isEmpty()) {
GEN_AND_CHECK(json_gen_keyvalue_cstring(gen, "url", node->url().utf8().data()));
GEN_AND_CHECK(json_gen_keyvalue_integer(gen, "lineNumber", node->lineNumber()));
GEN_AND_CHECK(json_gen_keyvalue_integer(gen, "columnNumber", node->columnNumber()));
}
GEN_AND_CHECK(json_gen_key_cstring(gen, "calls"));
GEN_AND_CHECK(json_gen_array_open(gen, json_entry_value));
for (const JSC::ProfileNode::Call &call : node->calls()) {
GEN_AND_CHECK(json_gen_map_open(gen, json_entry_key));
GEN_AND_CHECK(json_gen_keyvalue_double(gen, "startTime", call.startTime()));
#if IOS8
GEN_AND_CHECK(json_gen_keyvalue_double(gen, "totalTime", call.totalTime()));
#else
GEN_AND_CHECK(json_gen_keyvalue_double(gen, "totalTime", call.elapsedTime()));
#endif
GEN_AND_CHECK(json_gen_map_close(gen));
}
GEN_AND_CHECK(json_gen_array_close(gen));
if (!node->children().isEmpty()) {
GEN_AND_CHECK(json_gen_key_cstring(gen, "children"));
GEN_AND_CHECK(append_children_array_json(gen, node));
}
GEN_AND_CHECK(json_gen_map_close(gen));
return json_gen_status_ok;
}
static void convert_to_json(const JSC::Profile *profile, const char *filename) {
json_gen_status status;
json_gen gen = json_gen_alloc(filename);
status = append_root_json(gen, profile);
if (status != json_gen_status_ok) {
FILE *fileOut = fopen(filename, "wb");
if (fileOut != nullptr) {
fprintf(fileOut, "{\"error\": %d}", (int)status);
fclose(fileOut);
}
}
json_gen_free(gen);
}
// Based on JSEndProfiling, with a little extra code to return the profile as JSON.
static void JSEndProfilingAndRender(JSContextRef ctx, const char *title, const char *filename)
{
JSC::ExecState *exec = toJS(ctx);
JSC::LegacyProfiler *profiler = JSC::LegacyProfiler::profiler();
RefPtr<JSC::Profile> rawProfile = profiler->stopProfiling(exec, WTF::String(title));
convert_to_json(rawProfile.get(), filename);
}
extern "C" {
void nativeProfilerEnableBytecode(void)
{
JSC::Options::setOption("forceProfilerBytecodeGeneration=true");
}
void nativeProfilerStart(JSContextRef ctx, const char *title) {
JSStartProfiling(ctx, JSStringCreateWithUTF8CString(title));
}
void nativeProfilerEnd(JSContextRef ctx, const char *title, const char *filename) {
JSEndProfilingAndRender(ctx, title, filename);
}
}

View File

@ -1,18 +0,0 @@
ios9:
IOS_VERSION=9 \
JSC_VERSION=7601.1.46.3 \
WEB_CORE_VERSION=7601.1.46.10 \
WTF_VERSION=7601.1.46.3 \
make -f Makefile.base
ios8:
IOS_VERSION=8 \
JSC_VERSION=7600.1.17 \
WEB_CORE_VERSION=7600.1.25 \
WTF_VERSION=7600.1.24 \
make -f Makefile.base
.PHONY: clean
clean:
-rm -rf $(wildcard *.dylib)
-rm -rf download

View File

@ -1,80 +0,0 @@
HEADER_PATHS := `find download/JavaScriptCore/JavaScriptCore-$(JSC_VERSION) -name '*.h' | xargs -I{} dirname {} | uniq | xargs -I{} echo "-I {}"`
XCODE_PATH ?= $(shell xcode-select -p)
SDK_PATH = $(XCODE_PATH)/Platforms/$1.platform/Developer/SDKs/$1.sdk
SDK_VERSION = $(shell plutil -convert json -o - $(call SDK_PATH,iPhoneOS)/SDKSettings.plist | awk -f parseSDKVersion.awk)
CERT ?= iPhone Developer
ARCHS = x86_64 arm64 armv7 i386
PLATFORM = \
if [[ "$*" = "x86_64" || "$*" = "i386" ]]; then \
PLATFORM=iPhoneSimulator; \
else \
PLATFORM=iPhoneOS; \
fi;
SYSROOT = -isysroot $(call SDK_PATH,$${PLATFORM})
IOS_LIBS = \
download/JavaScriptCore/JavaScriptCore-$(JSC_VERSION) \
download/WebCore/WebCore-$(WEB_CORE_VERSION) \
download/WTF/WTF-$(WTF_VERSION) \
download/JavaScriptCore/JavaScriptCore-$(JSC_VERSION)/Bytecodes.h
IOS_EXT=ios$(IOS_VERSION)
ifneq ($(SDK_VERSION), $(IOS_VERSION))
all:
$(error "Expected to be compiled with iOS SDK version 8, found $(SDK_VERSION)")
else
all: RCTJSCProfiler.$(IOS_EXT).dylib /tmp/RCTJSCProfiler
cp $^
endif
/tmp/RCTJSCProfiler:
mkdir -p $@
RCTJSCProfiler.$(IOS_EXT).dylib: RCTJSCProfiler_unsigned.$(IOS_EXT).dylib
cp $< $@
codesign -f -s "${CERT}" $@
.PRECIOUS: RCTJSCProfiler_unsigned.$(IOS_EXT).dylib
RCTJSCProfiler_unsigned.$(IOS_EXT).dylib: $(patsubst %,RCTJSCProfiler_%.$(IOS_EXT).dylib,$(ARCHS))
lipo -create -output $@ $^
.PRECIOUS: RCTJSCProfiler_%.$(IOS_EXT).dylib
RCTJSCProfiler_%.$(IOS_EXT).dylib: $(IOS_LIBS)
$(PLATFORM) \
clang -w -dynamiclib -o RCTJSCProfiler_$*.$(IOS_EXT).dylib -std=c++11 \
-arch $* \
-install_name RCTJSCProfiler.$(IOS_EXT).dylib \
-include ./download/JavaScriptCore/JavaScriptCore-$(JSC_VERSION)/config.h \
-I download \
-I download/WebCore/WebCore-$(WEB_CORE_VERSION)/icu \
-I download/WTF/WTF-$(WTF_VERSION) \
-DNDEBUG=1 \
-DIOS$(IOS_VERSION)=1 \
-miphoneos-version-min=8.0 \
$(SYSROOT) \
$(HEADER_PATHS) \
-undefined dynamic_lookup \
JSCLegacyProfiler.mm
.PRECIOUS: %/Bytecodes.h
%/Bytecodes.h:
python $*/generate-bytecode-files --bytecodes_h $@ $*/bytecode/BytecodeList.json
.PRECIOUS: download/%
download/%: download/%.tar.gz
tar -zxvf $< -C `dirname $@` > /dev/null
.PRECIOUS: %.tar.gz
%.tar.gz:
mkdir -p `dirname $@`
curl -o $@ http://www.opensource.apple.com/tarballs/$(patsubst download/%,%,$@)

View File

@ -1,254 +0,0 @@
#!/usr/bin/env python
from __future__ import absolute_import
from __future__ import division
from __future__ import print_function
from __future__ import unicode_literals
import argparse
import json
import smap
import trace_data
import urllib
SECONDS_TO_NANOSECONDS = (1000*1000)
SAMPLE_DELTA_IN_SECONDS = 0.0001
class Marker(object):
def __init__(self, _name, _timestamp, _depth, _is_end, _ident, url, line, col):
self.name = _name
self.timestamp = _timestamp
self.depth = _depth
self.is_end = _is_end
self.ident = _ident
self.url = url
self.line = line
self.col = col
# sort markers making sure they are ordered by timestamp then depth of function call
# and finally that markers of the same ident are sorted in the order begin then end
def __cmp__(self, other):
if self.timestamp < other.timestamp:
return -1
if self.timestamp > other.timestamp:
return 1
if self.depth < other.depth:
return -1
if self.depth > other.depth:
return 1
if self.ident == other.ident:
if self.is_end:
return 1
return 0
# calculate marker name based on combination of function name and location
def _calcname(entry):
funcname = ""
if "functionName" in entry:
funcname = funcname + entry["functionName"]
return funcname
def _calcurl(mapcache, entry, map_file):
if entry.url not in mapcache:
map_url = entry.url.replace('.bundle', '.map')
if map_url != entry.url:
if map_file:
print('Loading sourcemap from:' + map_file)
map_url = map_file
try:
url_file = urllib.urlopen(map_url)
if url_file != None:
entries = smap.parse(url_file)
mapcache[entry.url] = entries
except Exception, e:
mapcache[entry.url] = []
if entry.url in mapcache:
source_entry = smap.find(mapcache[entry.url], entry.line, entry.col)
if source_entry:
entry.url = 'file://' + source_entry.src
entry.line = source_entry.src_line
entry.col = source_entry.src_col
def _compute_markers(markers, call_point, depth):
name = _calcname(call_point)
ident = len(markers)
url = ""
lineNumber = -1
columnNumber = -1
if "url" in call_point:
url = call_point["url"]
if "lineNumber" in call_point:
lineNumber = call_point["lineNumber"]
if "columnNumber" in call_point:
columnNumber = call_point["columnNumber"]
for call in call_point["calls"]:
markers.append(Marker(name, call["startTime"], depth, 0, ident, url, lineNumber, columnNumber))
markers.append(Marker(name, call["startTime"] + call["totalTime"], depth, 1, ident, url, lineNumber, columnNumber))
ident = ident + 2
if "children" in call_point:
for child in call_point["children"]:
_compute_markers(markers, child, depth+1);
def _find_child(children, name):
for child in children:
if child['functionName'] == name:
return child
return None
def _add_entry_cpuprofiler_program(newtime, cpuprofiler):
curnode = _find_child(cpuprofiler['head']['children'], '(program)')
if cpuprofiler['lastTime'] != None:
lastTime = cpuprofiler['lastTime']
while lastTime < newtime:
curnode['hitCount'] += 1
cpuprofiler['samples'].append(curnode['callUID'])
cpuprofiler['timestamps'].append(int(lastTime*SECONDS_TO_NANOSECONDS))
lastTime += SAMPLE_DELTA_IN_SECONDS
cpuprofiler['lastTime'] = lastTime
else:
cpuprofiler['lastTime'] = newtime
def _add_entry_cpuprofiler(stack, newtime, cpuprofiler):
index = len(stack) - 1
marker = stack[index]
if marker.name not in cpuprofiler['markers']:
cpuprofiler['markers'][marker.name] = cpuprofiler['id']
cpuprofiler['callUID'] += 1
callUID = cpuprofiler['markers'][marker.name]
curnode = cpuprofiler['head']
index = 0
while index < len(stack):
newnode = _find_child(curnode['children'], stack[index].name)
if newnode == None:
newnode = {}
newnode['callUID'] = callUID
newnode['url'] = marker.url
newnode['functionName'] = stack[index].name
newnode['hitCount'] = 0
newnode['lineNumber'] = marker.line
newnode['columnNumber'] = marker.col
newnode['scriptId'] = callUID
newnode['positionTicks'] = []
newnode['id'] = cpuprofiler['id']
cpuprofiler['id'] += 1
newnode['children'] = []
curnode['children'].append(newnode)
curnode['deoptReason'] = ''
curnode = newnode
index += 1
if cpuprofiler['lastTime'] == None:
cpuprofiler['lastTime'] = newtime
if cpuprofiler['lastTime'] != None:
lastTime = cpuprofiler['lastTime']
while lastTime < newtime:
curnode['hitCount'] += 1
if len(curnode['positionTicks']) == 0:
ticks = {}
ticks['line'] = curnode['callUID']
ticks['ticks'] = 0
curnode['positionTicks'].append(ticks)
curnode['positionTicks'][0]['ticks'] += 1
cpuprofiler['samples'].append(curnode['callUID'])
cpuprofiler['timestamps'].append(int(lastTime*1000*1000))
lastTime += 0.0001
cpuprofiler['lastTime'] = lastTime
def _create_default_cpuprofiler_node(name, _id, _uid):
return {'functionName': name,
'scriptId':'0',
'url':'',
'lineNumber':0,
'columnNumber':0,
'positionTicks':[],
'id':_id,
'callUID':_uid,
'children': [],
'hitCount': 0,
'deoptReason':''}
def main():
parser = argparse.ArgumentParser(description="Converts JSON profile format to fbsystrace text output")
parser.add_argument(
"-o",
dest = "output_file",
default = None,
help = "Output file for trace data")
parser.add_argument(
"-cpuprofiler",
dest = "output_cpuprofiler",
default = None,
help = "Output file for cpuprofiler data")
parser.add_argument(
"-map",
dest = "map_file",
default = None,
help = "Map file for symbolicating")
parser.add_argument( "file", help = "JSON trace input_file")
args = parser.parse_args()
markers = []
with open(args.file, "r") as trace_file:
trace = json.load(trace_file)
for root_entry in trace["rootNodes"]:
_compute_markers(markers, root_entry, 0)
mapcache = {}
for m in markers:
_calcurl(mapcache, m, args.map_file)
sorted_markers = list(sorted(markers));
if args.output_cpuprofiler != None:
cpuprofiler = {}
cpuprofiler['startTime'] = None
cpuprofiler['endTime'] = None
cpuprofiler['lastTime'] = None
cpuprofiler['id'] = 4
cpuprofiler['callUID'] = 4
cpuprofiler['samples'] = []
cpuprofiler['timestamps'] = []
cpuprofiler['markers'] = {}
cpuprofiler['head'] = _create_default_cpuprofiler_node('(root)', 1, 1)
cpuprofiler['head']['children'].append(_create_default_cpuprofiler_node('(root)', 2, 2))
cpuprofiler['head']['children'].append(_create_default_cpuprofiler_node('(program)', 3, 3))
marker_stack = []
with open(args.output_cpuprofiler, 'w') as file_out:
for marker in sorted_markers:
if len(marker_stack):
_add_entry_cpuprofiler(marker_stack, marker.timestamp, cpuprofiler)
else:
_add_entry_cpuprofiler_program(marker.timestamp, cpuprofiler)
if marker.is_end:
marker_stack.pop()
else:
marker_stack.append(marker)
cpuprofiler['startTime'] = cpuprofiler['timestamps'][0] / 1000000.0
cpuprofiler['endTime'] = cpuprofiler['timestamps'][len(cpuprofiler['timestamps']) - 1] / 1000000.0
json.dump(cpuprofiler, file_out, sort_keys=False, indent=4, separators=(',', ': '))
if args.output_file != None:
with open(args.output_file,"w") as trace_file:
for marker in sorted_markers:
start_or_end = None
if marker.is_end:
start_or_end = "E"
else:
start_or_end = "B"
#output with timestamp at high level of precision
trace_file.write("json-0 [000] .... {0:.12f}: tracing_mark_write: {1}|0|{2}\n".format(
marker.timestamp,
start_or_end,
marker.name))
main()

View File

@ -1,10 +0,0 @@
BEGIN {
FS = ":"
RS = ","
}
/"Version"/ {
version = substr($2, 2, length($2) - 2)
print int(version)
exit 0
}

View File

@ -1,343 +0,0 @@
from __future__ import absolute_import
from __future__ import division
from __future__ import print_function
from __future__ import unicode_literals
"""
adapted from https://github.com/martine/python-sourcemap into a reuasable module
"""
"""
Apache License
Version 2.0, January 2010
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright [yyyy] [name of copyright owner]
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
"""
"""A module for parsing source maps, as output by the Closure and
CoffeeScript compilers and consumed by browsers. See
http://www.html5rocks.com/en/tutorials/developertools/sourcemaps/
"""
import collections
import json
import sys
import bisect
class entry(object):
def __init__(self, dst_line, dst_col, src, src_line, src_col):
self.dst_line = dst_line
self.dst_col = dst_col
self.src = src
self.src_line = src_line
self.src_col = src_col
def __cmp__(self, other):
#print(self)
#print(other)
if self.dst_line < other.dst_line:
return -1
if self.dst_line > other.dst_line:
return 1
if self.dst_col < other.dst_col:
return -1
if self.dst_col > other.dst_col:
return 1
return 0
SmapState = collections.namedtuple(
'SmapState', ['dst_line', 'dst_col',
'src', 'src_line', 'src_col',
'name'])
# Mapping of base64 letter -> integer value.
B64 = dict((c, i) for i, c in
enumerate('ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz'
'0123456789+/'))
def _parse_vlq(segment):
"""Parse a string of VLQ-encoded data.
Returns:
a list of integers.
"""
values = []
cur, shift = 0, 0
for c in segment:
val = B64[c]
# Each character is 6 bits:
# 5 of value and the high bit is the continuation.
val, cont = val & 0b11111, val >> 5
cur += val << shift
shift += 5
if not cont:
# The low bit of the unpacked value is the sign.
cur, sign = cur >> 1, cur & 1
if sign:
cur = -cur
values.append(cur)
cur, shift = 0, 0
if cur or shift:
raise Exception('leftover cur/shift in vlq decode')
return values
def _parse_smap(file):
"""Given a file-like object, yield SmapState()s as they are read from it."""
smap = json.load(file)
sources = smap['sources']
names = smap['names']
mappings = smap['mappings']
lines = mappings.split(';')
dst_col, src_id, src_line, src_col, name_id = 0, 0, 0, 0, 0
for dst_line, line in enumerate(lines):
segments = line.split(',')
dst_col = 0
for segment in segments:
if not segment:
continue
parsed = _parse_vlq(segment)
dst_col += parsed[0]
src = None
name = None
if len(parsed) > 1:
src_id += parsed[1]
src = sources[src_id]
src_line += parsed[2]
src_col += parsed[3]
if len(parsed) > 4:
name_id += parsed[4]
name = names[name_id]
assert dst_line >= 0
assert dst_col >= 0
assert src_line >= 0
assert src_col >= 0
yield SmapState(dst_line, dst_col, src, src_line, src_col, name)
def find(entries, line, col):
test = entry(line, col, '', 0, 0)
index = bisect.bisect_right(entries, test)
if index == 0:
return None
return entries[index - 1]
def parse(file):
# Simple demo that shows files that most contribute to total size.
lookup = []
for state in _parse_smap(file):
lookup.append(entry(state.dst_line, state.dst_col, state.src, state.src_line, state.src_col))
sorted_lookup = list(sorted(lookup))
return sorted_lookup

View File

@ -1,244 +0,0 @@
from __future__ import absolute_import
from __future__ import division
from __future__ import print_function
from __future__ import unicode_literals
import re
import unittest
"""
# _-----=> irqs-off
# / _----=> need-resched
# | / _---=> hardirq/softirq
# || / _--=> preempt-depth
# ||| / delay
# TASK-PID CPU# |||| TIMESTAMP FUNCTION
# | | | |||| | |
<idle>-0 [001] ...2 3269.291072: sched_switch: prev_comm=swapper/1 prev_pid=0 prev_prio=120 prev_state=R ==> next_comm=mmcqd/0 next_pid=120 next_prio=120
"""
TRACE_LINE_PATTERN = re.compile(
r'^\s*(?P<task>.+)-(?P<pid>\d+)\s+(?:\((?P<tgid>.+)\)\s+)?\[(?P<cpu>\d+)\]\s+(?:(?P<flags>\S{4})\s+)?(?P<timestamp>[0-9.]+):\s+(?P<function>.+)$')
"""
Example lines from custom app traces:
0: B|27295|providerRemove
0: E
tracing_mark_write: S|27311|NNFColdStart<D-7744962>|1112249168
"""
APP_TRACE_LINE_PATTERN = re.compile(
r'^(?P<type>.+?): (?P<args>.+)$')
"""
Example section names:
NNFColdStart
NNFColdStart<0><T7744962>
NNFColdStart<X>
NNFColdStart<T7744962>
"""
DECORATED_SECTION_NAME_PATTERN = re.compile(r'^(?P<section_name>.*?)(?:<0>)?(?:<(?P<command>.)(?P<argument>.*?)>)?$')
SYSTRACE_LINE_TYPES = set(['0', 'tracing_mark_write'])
class TraceLine(object):
def __init__(self, task, pid, tgid, cpu, flags, timestamp, function):
self.task = task
self.pid = pid
self.tgid = tgid
self.cpu = cpu
self.flags = flags
self.timestamp = timestamp
self.function = function
self.canceled = False
@property
def is_app_trace_line(self):
return isinstance(self.function, AppTraceFunction)
def cancel(self):
self.canceled = True
def __str__(self):
if self.canceled:
return ""
elif self.tgid:
return "{task:>16s}-{pid:<5d} ({tgid:5s}) [{cpu:03d}] {flags:4s} {timestamp:12f}: {function}\n".format(**vars(self))
elif self.flags:
return "{task:>16s}-{pid:<5d} [{cpu:03d}] {flags:4s} {timestamp:12f}: {function}\n".format(**vars(self))
else:
return "{task:>16s}-{pid:<5d} [{cpu:03d}] {timestamp:12.6f}: {function}\n".format(**vars(self))
class AppTraceFunction(object):
def __init__(self, type, args):
self.type = type
self.args = args
self.operation = args[0]
if len(args) >= 2 and args[1]:
self.pid = int(args[1])
if len(args) >= 3:
self._section_name, self.command, self.argument = _parse_section_name(args[2])
args[2] = self._section_name
else:
self._section_name = None
self.command = None
self.argument = None
self.cookie = None
@property
def section_name(self):
return self._section_name
@section_name.setter
def section_name(self, value):
self._section_name = value
self.args[2] = value
def __str__(self):
return "{type}: {args}".format(type=self.type, args='|'.join(self.args))
class AsyncTraceFunction(AppTraceFunction):
def __init__(self, type, args):
super(AsyncTraceFunction, self).__init__(type, args)
self.cookie = int(args[3])
TRACE_TYPE_MAP = {
'S': AsyncTraceFunction,
'T': AsyncTraceFunction,
'F': AsyncTraceFunction,
}
def parse_line(line):
match = TRACE_LINE_PATTERN.match(line.strip())
if not match:
return None
task = match.group("task")
pid = int(match.group("pid"))
tgid = match.group("tgid")
cpu = int(match.group("cpu"))
flags = match.group("flags")
timestamp = float(match.group("timestamp"))
function = match.group("function")
app_trace = _parse_function(function)
if app_trace:
function = app_trace
return TraceLine(task, pid, tgid, cpu, flags, timestamp, function)
def parse_dextr_line(line):
task = line["name"]
pid = line["pid"]
tgid = line["tid"]
cpu = None
flags = None
timestamp = line["ts"]
function = AppTraceFunction("DextrTrace", [line["ph"], line["pid"], line["name"]])
return TraceLine(task, pid, tgid, cpu, flags, timestamp, function)
def _parse_function(function):
line_match = APP_TRACE_LINE_PATTERN.match(function)
if not line_match:
return None
type = line_match.group("type")
if not type in SYSTRACE_LINE_TYPES:
return None
args = line_match.group("args").split('|')
if len(args) == 1 and len(args[0]) == 0:
args = None
constructor = TRACE_TYPE_MAP.get(args[0], AppTraceFunction)
return constructor(type, args)
def _parse_section_name(section_name):
if section_name is None:
return section_name, None, None
section_name_match = DECORATED_SECTION_NAME_PATTERN.match(section_name)
section_name = section_name_match.group("section_name")
command = section_name_match.group("command")
argument = section_name_match.group("argument")
return section_name, command, argument
def _format_section_name(section_name, command, argument):
if not command:
return section_name
return "{section_name}<{command}{argument}>".format(**vars())
class RoundTripFormattingTests(unittest.TestCase):
def testPlainSectionName(self):
section_name = "SectionName12345-5562342fas"
self.assertEqual(section_name, _format_section_name(*_parse_section_name(section_name)))
def testDecoratedSectionName(self):
section_name = "SectionName12345-5562342fas<D-123456>"
self.assertEqual(section_name, _format_section_name(*_parse_section_name(section_name)))
def testSimpleFunction(self):
function = "0: E"
self.assertEqual(function, str(_parse_function(function)))
def testFunctionWithoutCookie(self):
function = "0: B|27295|providerRemove"
self.assertEqual(function, str(_parse_function(function)))
def testFunctionWithCookie(self):
function = "0: S|27311|NNFColdStart|1112249168"
self.assertEqual(function, str(_parse_function(function)))
def testFunctionWithCookieAndArgs(self):
function = "0: T|27311|NNFColdStart|1122|Start"
self.assertEqual(function, str(_parse_function(function)))
def testFunctionWithArgsButNoPid(self):
function = "0: E|||foo=bar"
self.assertEqual(function, str(_parse_function(function)))
def testKitKatFunction(self):
function = "tracing_mark_write: B|14127|Looper.dispatchMessage|arg=>>>>> Dispatching to Handler (android.os.Handler) {422ae980} null: 0|Java"
self.assertEqual(function, str(_parse_function(function)))
def testNonSysTraceFunctionIgnored(self):
function = "sched_switch: prev_comm=swapper/1 prev_pid=0 prev_prio=120 prev_state=R ==> next_comm=mmcqd/0 next_pid=120 next_prio=120"
self.assertEqual(None, _parse_function(function))
def testLineWithFlagsAndTGID(self):
line = " <idle>-0 ( 550) [000] d..2 7953.258473: cpu_idle: state=1 cpu_id=0\n"
self.assertEqual(line, str(parse_line(line)))
def testLineWithFlagsAndNoTGID(self):
line = " <idle>-0 (-----) [000] d..2 7953.258473: cpu_idle: state=1 cpu_id=0\n"
self.assertEqual(line, str(parse_line(line)))
def testLineWithFlags(self):
line = " <idle>-0 [001] ...2 3269.291072: sched_switch: prev_comm=swapper/1 prev_pid=0 prev_prio=120 prev_state=R ==> next_comm=mmcqd/0 next_pid=120 next_prio=120\n"
self.assertEqual(line, str(parse_line(line)))
def testLineWithoutFlags(self):
line = " <idle>-0 [001] 3269.291072: sched_switch: prev_comm=swapper/1 prev_pid=0 prev_prio=120 prev_state=R ==> next_comm=mmcqd/0 next_pid=120 next_prio=120\n"
self.assertEqual(line, str(parse_line(line)))

View File

@ -1,43 +0,0 @@
/**
* Copyright (c) 2015-present, Facebook, Inc.
* All rights reserved.
*
* This source code is licensed under the BSD-style license found in the
* LICENSE file in the root directory of this source tree. An additional grant
* of patent rights can be found in the PATENTS file in the same directory.
*
* @providesModule CPUProfiler
* @flow
*/
'use strict';
var _label;
var _nestingLevel = 0;
var CPUProfiler = {
start(profileName: string) {
if (_nestingLevel === 0) {
if (global.nativeProfilerStart) {
_label = profileName;
global.nativeProfilerStart(profileName);
} else if (console.profile) {
console.profile(profileName);
}
}
_nestingLevel++;
},
end() {
_nestingLevel--;
if (_nestingLevel === 0) {
if (global.nativeProfilerEnd) {
global.nativeProfilerEnd(_label);
} else if (console.profileEnd) {
console.profileEnd();
}
_label = undefined;
}
}
};
module.exports = CPUProfiler;

View File

@ -117,13 +117,6 @@ public:
callback:m_errorBlock];
}
virtual bool supportsProfiling() override {
return false;
};
virtual void startProfiler(const std::string &titleString) override {};
virtual void stopProfiler(const std::string &titleString,
const std::string &filename) override {};
private:
id<RCTJavaScriptExecutor> m_jse;
RCTJavaScriptCompleteBlock m_errorBlock;

View File

@ -30,8 +30,6 @@
#import <React/RCTProfile.h>
#import <React/RCTUtils.h>
#import "RCTJSCProfiler.h"
#if (RCT_PROFILE || RCT_DEV) && __has_include("RCTDevMenu.h")
#import "RCTDevMenu.h"
#endif
@ -164,34 +162,6 @@ RCT_NOT_IMPLEMENTED(-(instancetype)init)
RCT_EXPORT_MODULE()
#if RCT_DEV
static void RCTInstallJSCProfiler(RCTBridge *bridge, JSContextRef context)
{
#if __has_include("RCTDevMenu.h")
__weak RCTBridge *weakBridge = bridge;
__weak RCTDevSettings *devSettings = bridge.devSettings;
if (RCTJSCProfilerIsSupported()) {
[bridge.devMenu addItem:[RCTDevMenuItem buttonItemWithTitleBlock:^NSString *{
return devSettings.isJSCProfilingEnabled ? @"Stop Profiling" : @"Start Profiling";
} handler:^{
BOOL shouldStart = !devSettings.isJSCProfilingEnabled;
devSettings.isJSCProfilingEnabled = shouldStart;
if (shouldStart != RCTJSCProfilerIsProfiling(context)) {
if (shouldStart) {
RCTJSCProfilerStart(context);
} else {
NSString *outputFile = RCTJSCProfilerStop(context);
NSData *profileData = [NSData dataWithContentsOfFile:outputFile options:NSDataReadingMappedIfSafe error:NULL];
RCTProfileSendResult(weakBridge, @"cpu-profile", profileData);
}
}
}]];
}
#endif
}
#endif
+ (void)runRunLoopThread
{
@autoreleasepool {
@ -420,8 +390,6 @@ static NSThread *newJavaScriptThread(void)
#endif
#if RCT_DEV
RCTInstallJSCProfiler(self->_bridge, context.JSGlobalContextRef);
// Inject handler used by HMR
context[@"nativeInjectHMRUpdate"] = ^(NSString *sourceCode, NSString *sourceCodeURL) {
RCTJSCExecutor *strongSelf = weakSelf;

View File

@ -92,11 +92,6 @@
*/
@property (nonatomic, assign) BOOL isPerfMonitorShown;
/**
* Whether JSC profiling is enabled.
*/
@property (nonatomic, assign) BOOL isJSCProfilingEnabled;
#if RCT_DEV
- (void)addHandler:(id<RCTPackagerClientMethod>)handler forPackagerMethod:(NSString *)name;

View File

@ -32,7 +32,6 @@ NSString *const kRCTDevSettingIsDebuggingRemotely = @"isDebuggingRemotely";
NSString *const kRCTDevSettingExecutorOverrideClass = @"executor-override";
NSString *const kRCTDevSettingShakeToShowDevMenu = @"shakeToShow";
NSString *const kRCTDevSettingIsPerfMonitorShown = @"RCTPerfMonitorKey";
NSString *const kRCTDevSettingIsJSCProfilingEnabled = @"RCTJSCProfilerEnabled";
NSString *const kRCTDevSettingStartSamplingProfilerOnLaunch = @"startSamplingProfilerOnLaunch";
NSString *const kRCTDevSettingsUserDefaultsKey = @"RCTDevMenu";
@ -373,16 +372,6 @@ RCT_EXPORT_METHOD(toggleElementInspector)
return [[self settingForKey:kRCTDevSettingIsPerfMonitorShown] boolValue];
}
- (void)setIsJSCProfilingEnabled:(BOOL)isJSCProfilingEnabled
{
[self _updateSettingWithValue:@(isJSCProfilingEnabled) forKey:kRCTDevSettingIsJSCProfilingEnabled];
}
- (BOOL)isJSCProfilingEnabled
{
return [[self settingForKey:kRCTDevSettingIsJSCProfilingEnabled] boolValue];
}
- (void)setStartSamplingProfilerOnLaunch:(BOOL)startSamplingProfilerOnLaunch
{
[self _updateSettingWithValue:@(startSamplingProfilerOnLaunch) forKey:kRCTDevSettingStartSamplingProfilerOnLaunch];

View File

@ -1,22 +0,0 @@
/**
* Copyright (c) 2015-present, Facebook, Inc.
* All rights reserved.
*
* This source code is licensed under the BSD-style license found in the
* LICENSE file in the root directory of this source tree. An additional grant
* of patent rights can be found in the PATENTS file in the same directory.
*/
#import <JavaScriptCore/JavaScriptCore.h>
#import <React/RCTDefines.h>
/** The API is not thread-safe. */
/** The context is not retained. */
RCT_EXTERN void RCTJSCProfilerStart(JSContextRef ctx);
/** Returns a file path containing the profiler data. */
RCT_EXTERN NSString *RCTJSCProfilerStop(JSContextRef ctx);
RCT_EXTERN BOOL RCTJSCProfilerIsProfiling(JSContextRef ctx);
RCT_EXTERN BOOL RCTJSCProfilerIsSupported(void);

View File

@ -1,135 +0,0 @@
/**
* Copyright (c) 2015-present, Facebook, Inc.
* All rights reserved.
*
* This source code is licensed under the BSD-style license found in the
* LICENSE file in the root directory of this source tree. An additional grant
* of patent rights can be found in the PATENTS file in the same directory.
*/
#import "RCTJSCProfiler.h"
#import <UIKit/UIKit.h>
#import <React/RCTLog.h>
#ifndef RCT_JSC_PROFILER
#define RCT_JSC_PROFILER RCT_PROFILE
#endif
#if RCT_JSC_PROFILER
#include <dlfcn.h>
#ifndef RCT_JSC_PROFILER_DYLIB
#define RCT_JSC_PROFILER_DYLIB [[[NSBundle mainBundle] pathForResource:[NSString stringWithFormat:@"RCTJSCProfiler.ios%zd", [[[UIDevice currentDevice] systemVersion] integerValue]] ofType:@"dylib" inDirectory:@"RCTJSCProfiler"] UTF8String]
#endif
static const char *const JSCProfileName = "profile";
typedef void (*JSCProfilerStartFunctionType)(JSContextRef, const char *);
typedef void (*JSCProfilerEndFunctionType)(JSContextRef, const char *, const char *);
typedef void (*JSCProfilerEnableFunctionType)(void);
static NSMutableDictionary<NSValue *, NSNumber *> *RCTJSCProfilerStateMap;
static JSCProfilerStartFunctionType RCTNativeProfilerStart = NULL;
static JSCProfilerEndFunctionType RCTNativeProfilerEnd = NULL;
NS_INLINE NSValue *RCTJSContextRefKey(JSContextRef ref) {
return [NSValue valueWithPointer:ref];
}
static void RCTJSCProfilerStateInit()
{
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
RCTJSCProfilerStateMap = [NSMutableDictionary new];
void *JSCProfiler = dlopen(RCT_JSC_PROFILER_DYLIB, RTLD_NOW);
RCTNativeProfilerStart = (JSCProfilerStartFunctionType)dlsym(JSCProfiler, "nativeProfilerStart");
RCTNativeProfilerEnd = (JSCProfilerEndFunctionType)dlsym(JSCProfiler, "nativeProfilerEnd");
JSCProfilerEnableFunctionType enableBytecode = (__typeof__(enableBytecode))dlsym(JSCProfiler, "nativeProfilerEnableBytecode");
if (RCTNativeProfilerStart && RCTNativeProfilerEnd && enableBytecode) {
enableBytecode();
} else {
RCTNativeProfilerStart = NULL;
RCTNativeProfilerEnd = NULL;
}
});
}
#endif
void RCTJSCProfilerStart(JSContextRef ctx)
{
#if RCT_JSC_PROFILER
if (ctx != NULL) {
if (RCTJSCProfilerIsSupported()) {
NSValue *key = RCTJSContextRefKey(ctx);
BOOL isProfiling = [RCTJSCProfilerStateMap[key] boolValue];
if (!isProfiling) {
RCTLogInfo(@"Starting JSC profiler for context: %p", ctx);
RCTJSCProfilerStateMap[key] = @YES;
RCTNativeProfilerStart(ctx, JSCProfileName);
} else {
RCTLogWarn(@"Trying to start JSC profiler on a context which is already profiled.");
}
} else {
RCTLogWarn(@"Cannot start JSC profiler as it's not supported.");
}
} else {
RCTLogWarn(@"Trying to start JSC profiler for NULL context.");
}
#endif
}
NSString *RCTJSCProfilerStop(JSContextRef ctx)
{
NSString *outputFile = nil;
#if RCT_JSC_PROFILER
if (ctx != NULL) {
RCTJSCProfilerStateInit();
NSValue *key = RCTJSContextRefKey(ctx);
BOOL isProfiling = [RCTJSCProfilerStateMap[key] boolValue];
if (isProfiling) {
NSString *filename = [NSString stringWithFormat:@"cpu_profile_%ld.json", (long)CFAbsoluteTimeGetCurrent()];
outputFile = [NSTemporaryDirectory() stringByAppendingPathComponent:filename];
if (RCTNativeProfilerEnd) {
RCTNativeProfilerEnd(ctx, JSCProfileName, outputFile.UTF8String);
}
RCTLogInfo(@"Stopped JSC profiler for context: %p", ctx);
} else {
RCTLogWarn(@"Trying to stop JSC profiler on a context which is not being profiled.");
}
[RCTJSCProfilerStateMap removeObjectForKey:key];
} else {
RCTLogWarn(@"Trying to stop JSC profiler for NULL context.");
}
#endif
return outputFile;
}
BOOL RCTJSCProfilerIsProfiling(JSContextRef ctx)
{
BOOL isProfiling = NO;
#if RCT_JSC_PROFILER
if (ctx != NULL) {
RCTJSCProfilerStateInit();
isProfiling = [RCTJSCProfilerStateMap[RCTJSContextRefKey(ctx)] boolValue];
}
#endif
return isProfiling;
}
BOOL RCTJSCProfilerIsSupported(void)
{
BOOL isSupported = NO;
#if RCT_JSC_PROFILER
RCTJSCProfilerStateInit();
isSupported = (RCTNativeProfilerStart != NULL);
#endif
return isSupported;
}

View File

@ -160,7 +160,6 @@
13F887701E29726200C3C7A1 /* Instance.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3D92B0AE1E03699D0018521A /* Instance.cpp */; };
13F887711E29726200C3C7A1 /* JSBundleType.cpp in Sources */ = {isa = PBXBuildFile; fileRef = AC70D2EB1DE48A22002E6351 /* JSBundleType.cpp */; };
13F887721E29726200C3C7A1 /* JSCExecutor.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3D92B0B21E03699D0018521A /* JSCExecutor.cpp */; };
13F887731E29726200C3C7A1 /* JSCLegacyProfiler.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3D92B0B41E03699D0018521A /* JSCLegacyProfiler.cpp */; };
13F887741E29726200C3C7A1 /* JSCLegacyTracing.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3D92B0B61E03699D0018521A /* JSCLegacyTracing.cpp */; };
13F887751E29726200C3C7A1 /* JSCMemory.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3D92B0B81E03699D0018521A /* JSCMemory.cpp */; };
13F887761E29726200C3C7A1 /* JSCNativeModules.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3D92B0BA1E03699D0018521A /* JSCNativeModules.cpp */; };
@ -176,7 +175,6 @@
13F887821E29726300C3C7A1 /* CxxNativeModule.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3D92B0A81E03699D0018521A /* CxxNativeModule.cpp */; };
13F887841E29726300C3C7A1 /* Instance.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3D92B0AE1E03699D0018521A /* Instance.cpp */; };
13F887851E29726300C3C7A1 /* JSCExecutor.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3D92B0B21E03699D0018521A /* JSCExecutor.cpp */; };
13F887861E29726300C3C7A1 /* JSCLegacyProfiler.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3D92B0B41E03699D0018521A /* JSCLegacyProfiler.cpp */; };
13F887871E29726300C3C7A1 /* JSCLegacyTracing.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3D92B0B61E03699D0018521A /* JSCLegacyTracing.cpp */; };
13F887881E29726300C3C7A1 /* JSCMemory.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3D92B0B81E03699D0018521A /* JSCMemory.cpp */; };
13F887891E29726300C3C7A1 /* JSCNativeModules.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3D92B0BA1E03699D0018521A /* JSCNativeModules.cpp */; };
@ -229,7 +227,6 @@
27595AAA1E575C7800CCE2B1 /* JsArgumentHelpers-inl.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B01E03699D0018521A /* JsArgumentHelpers-inl.h */; };
27595AAB1E575C7800CCE2B1 /* JsArgumentHelpers.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B11E03699D0018521A /* JsArgumentHelpers.h */; };
27595AAC1E575C7800CCE2B1 /* JSCExecutor.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B31E03699D0018521A /* JSCExecutor.h */; };
27595AAD1E575C7800CCE2B1 /* JSCLegacyProfiler.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B51E03699D0018521A /* JSCLegacyProfiler.h */; };
27595AAE1E575C7800CCE2B1 /* JSCLegacyTracing.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B71E03699D0018521A /* JSCLegacyTracing.h */; };
27595AAF1E575C7800CCE2B1 /* JSCMemory.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B91E03699D0018521A /* JSCMemory.h */; };
27595AB01E575C7800CCE2B1 /* JSCNativeModules.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0BB1E03699D0018521A /* JSCNativeModules.h */; };
@ -252,7 +249,6 @@
27595AC51E575C7800CCE2B1 /* JsArgumentHelpers-inl.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B01E03699D0018521A /* JsArgumentHelpers-inl.h */; };
27595AC61E575C7800CCE2B1 /* JsArgumentHelpers.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B11E03699D0018521A /* JsArgumentHelpers.h */; };
27595AC71E575C7800CCE2B1 /* JSCExecutor.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B31E03699D0018521A /* JSCExecutor.h */; };
27595AC81E575C7800CCE2B1 /* JSCLegacyProfiler.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B51E03699D0018521A /* JSCLegacyProfiler.h */; };
27595AC91E575C7800CCE2B1 /* JSCLegacyTracing.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B71E03699D0018521A /* JSCLegacyTracing.h */; };
27595ACA1E575C7800CCE2B1 /* JSCMemory.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B91E03699D0018521A /* JSCMemory.h */; };
27595ACB1E575C7800CCE2B1 /* JSCNativeModules.h in Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0BB1E03699D0018521A /* JSCNativeModules.h */; };
@ -805,7 +801,6 @@
3DA981A81E5B0E34004F2374 /* JSBigString.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D7454781E54757500E74ADD /* JSBigString.h */; };
3DA981A91E5B0E34004F2374 /* JSBundleType.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D3CD8F51DE5FB2300167DC4 /* JSBundleType.h */; };
3DA981AA1E5B0E34004F2374 /* JSCExecutor.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B31E03699D0018521A /* JSCExecutor.h */; };
3DA981AB1E5B0E34004F2374 /* JSCLegacyProfiler.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B51E03699D0018521A /* JSCLegacyProfiler.h */; };
3DA981AC1E5B0E34004F2374 /* JSCLegacyTracing.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B71E03699D0018521A /* JSCLegacyTracing.h */; };
3DA981AD1E5B0E34004F2374 /* JSCMemory.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B91E03699D0018521A /* JSCMemory.h */; };
3DA981AE1E5B0E34004F2374 /* JSCNativeModules.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0BB1E03699D0018521A /* JSCNativeModules.h */; };
@ -944,7 +939,6 @@
3DA982431E5B1053004F2374 /* JSBigString.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D7454781E54757500E74ADD /* JSBigString.h */; };
3DA982441E5B1053004F2374 /* JSBundleType.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D3CD8F51DE5FB2300167DC4 /* JSBundleType.h */; };
3DA982451E5B1053004F2374 /* JSCExecutor.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B31E03699D0018521A /* JSCExecutor.h */; };
3DA982461E5B1053004F2374 /* JSCLegacyProfiler.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B51E03699D0018521A /* JSCLegacyProfiler.h */; };
3DA982471E5B1053004F2374 /* JSCLegacyTracing.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B71E03699D0018521A /* JSCLegacyTracing.h */; };
3DA982481E5B1053004F2374 /* JSCMemory.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0B91E03699D0018521A /* JSCMemory.h */; };
3DA982491E5B1053004F2374 /* JSCNativeModules.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D92B0BB1E03699D0018521A /* JSCNativeModules.h */; };
@ -1350,7 +1344,6 @@
3DA982431E5B1053004F2374 /* JSBigString.h in Copy Headers */,
3DA982441E5B1053004F2374 /* JSBundleType.h in Copy Headers */,
3DA982451E5B1053004F2374 /* JSCExecutor.h in Copy Headers */,
3DA982461E5B1053004F2374 /* JSCLegacyProfiler.h in Copy Headers */,
3DA982471E5B1053004F2374 /* JSCLegacyTracing.h in Copy Headers */,
3DA982481E5B1053004F2374 /* JSCMemory.h in Copy Headers */,
3DA982491E5B1053004F2374 /* JSCNativeModules.h in Copy Headers */,
@ -1568,7 +1561,6 @@
3DA981A81E5B0E34004F2374 /* JSBigString.h in Copy Headers */,
3DA981A91E5B0E34004F2374 /* JSBundleType.h in Copy Headers */,
3DA981AA1E5B0E34004F2374 /* JSCExecutor.h in Copy Headers */,
3DA981AB1E5B0E34004F2374 /* JSCLegacyProfiler.h in Copy Headers */,
3DA981AC1E5B0E34004F2374 /* JSCLegacyTracing.h in Copy Headers */,
3DA981AD1E5B0E34004F2374 /* JSCMemory.h in Copy Headers */,
3DA981AE1E5B0E34004F2374 /* JSCNativeModules.h in Copy Headers */,
@ -1900,8 +1892,6 @@
3D92B0B11E03699D0018521A /* JsArgumentHelpers.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JsArgumentHelpers.h; sourceTree = "<group>"; };
3D92B0B21E03699D0018521A /* JSCExecutor.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = JSCExecutor.cpp; sourceTree = "<group>"; };
3D92B0B31E03699D0018521A /* JSCExecutor.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JSCExecutor.h; sourceTree = "<group>"; };
3D92B0B41E03699D0018521A /* JSCLegacyProfiler.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = JSCLegacyProfiler.cpp; sourceTree = "<group>"; };
3D92B0B51E03699D0018521A /* JSCLegacyProfiler.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JSCLegacyProfiler.h; sourceTree = "<group>"; };
3D92B0B61E03699D0018521A /* JSCLegacyTracing.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = JSCLegacyTracing.cpp; sourceTree = "<group>"; };
3D92B0B71E03699D0018521A /* JSCLegacyTracing.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JSCLegacyTracing.h; sourceTree = "<group>"; };
3D92B0B81E03699D0018521A /* JSCMemory.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = JSCMemory.cpp; sourceTree = "<group>"; };
@ -2654,8 +2644,6 @@
3D3CD8F51DE5FB2300167DC4 /* JSBundleType.h */,
3D92B0B21E03699D0018521A /* JSCExecutor.cpp */,
3D92B0B31E03699D0018521A /* JSCExecutor.h */,
3D92B0B41E03699D0018521A /* JSCLegacyProfiler.cpp */,
3D92B0B51E03699D0018521A /* JSCLegacyProfiler.h */,
3D92B0B61E03699D0018521A /* JSCLegacyTracing.cpp */,
3D92B0B71E03699D0018521A /* JSCLegacyTracing.h */,
3D92B0B81E03699D0018521A /* JSCMemory.cpp */,
@ -2882,7 +2870,6 @@
files = (
3D74547E1E54759A00E74ADD /* JSModulesUnbundle.h in Headers */,
27595AD51E575C7800CCE2B1 /* NativeToJsBridge.h in Headers */,
27595AC81E575C7800CCE2B1 /* JSCLegacyProfiler.h in Headers */,
27595AC41E575C7800CCE2B1 /* Instance.h in Headers */,
27595AD11E575C7800CCE2B1 /* MessageQueueThread.h in Headers */,
27595ACE1E575C7800CCE2B1 /* JSCUtils.h in Headers */,
@ -2971,7 +2958,6 @@
files = (
3D74547F1E54759E00E74ADD /* JSModulesUnbundle.h in Headers */,
27595ABA1E575C7800CCE2B1 /* NativeToJsBridge.h in Headers */,
27595AAD1E575C7800CCE2B1 /* JSCLegacyProfiler.h in Headers */,
27595AA91E575C7800CCE2B1 /* Instance.h in Headers */,
27595AB61E575C7800CCE2B1 /* MessageQueueThread.h in Headers */,
27595AB31E575C7800CCE2B1 /* JSCUtils.h in Headers */,
@ -3788,7 +3774,6 @@
13F887741E29726200C3C7A1 /* JSCLegacyTracing.cpp in Sources */,
13F887771E29726200C3C7A1 /* JSCPerfStats.cpp in Sources */,
13F887711E29726200C3C7A1 /* JSBundleType.cpp in Sources */,
13F887731E29726200C3C7A1 /* JSCLegacyProfiler.cpp in Sources */,
13F887791E29726200C3C7A1 /* JSCUtils.cpp in Sources */,
13F887781E29726200C3C7A1 /* JSCSamplingProfiler.cpp in Sources */,
13F887751E29726200C3C7A1 /* JSCMemory.cpp in Sources */,
@ -3812,7 +3797,6 @@
13F887871E29726300C3C7A1 /* JSCLegacyTracing.cpp in Sources */,
13F8878A1E29726300C3C7A1 /* JSCPerfStats.cpp in Sources */,
13F887841E29726300C3C7A1 /* Instance.cpp in Sources */,
13F887861E29726300C3C7A1 /* JSCLegacyProfiler.cpp in Sources */,
13F8878C1E29726300C3C7A1 /* JSCUtils.cpp in Sources */,
13F8878B1E29726300C3C7A1 /* JSCSamplingProfiler.cpp in Sources */,
13F887881E29726300C3C7A1 /* JSCMemory.cpp in Sources */,

View File

@ -68,7 +68,6 @@
1450FF871BCFF28A00208362 /* RCTProfileTrampoline-arm.S in Sources */ = {isa = PBXBuildFile; fileRef = 1450FF821BCFF28A00208362 /* RCTProfileTrampoline-arm.S */; };
1450FF881BCFF28A00208362 /* RCTProfileTrampoline-arm64.S in Sources */ = {isa = PBXBuildFile; fileRef = 1450FF831BCFF28A00208362 /* RCTProfileTrampoline-arm64.S */; };
1450FF8A1BCFF28A00208362 /* RCTProfileTrampoline-x86_64.S in Sources */ = {isa = PBXBuildFile; fileRef = 1450FF851BCFF28A00208362 /* RCTProfileTrampoline-x86_64.S */; };
14A43DF31C20B1C900794BC8 /* RCTJSCProfiler.m in Sources */ = {isa = PBXBuildFile; fileRef = 14A43DF21C20B1C900794BC8 /* RCTJSCProfiler.m */; };
14C2CA711B3AC63800E6CBB2 /* RCTModuleMethod.m in Sources */ = {isa = PBXBuildFile; fileRef = 14C2CA701B3AC63800E6CBB2 /* RCTModuleMethod.m */; };
14C2CA741B3AC64300E6CBB2 /* RCTModuleData.mm in Sources */ = {isa = PBXBuildFile; fileRef = 14C2CA731B3AC64300E6CBB2 /* RCTModuleData.mm */; };
14C2CA761B3AC64F00E6CBB2 /* RCTFrameUpdate.m in Sources */ = {isa = PBXBuildFile; fileRef = 14C2CA751B3AC64F00E6CBB2 /* RCTFrameUpdate.m */; };
@ -120,7 +119,6 @@
2D3B5EBC1D9B092600451313 /* RCTKeyboardObserver.m in Sources */ = {isa = PBXBuildFile; fileRef = 13D9FEED1CDCD93000158BD7 /* RCTKeyboardObserver.m */; };
2D3B5EBD1D9B092A00451313 /* RCTTiming.m in Sources */ = {isa = PBXBuildFile; fileRef = 13B07FEE1A69327A00A75B9A /* RCTTiming.m */; };
2D3B5EBE1D9B092D00451313 /* RCTUIManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 13E067491A70F434002CDEE1 /* RCTUIManager.m */; };
2D3B5EBF1D9B093300451313 /* RCTJSCProfiler.m in Sources */ = {isa = PBXBuildFile; fileRef = 14A43DF21C20B1C900794BC8 /* RCTJSCProfiler.m */; };
2D3B5EC01D9B093600451313 /* RCTPerfMonitor.m in Sources */ = {isa = PBXBuildFile; fileRef = 14F7A0EB1BDA3B3C003C6C10 /* RCTPerfMonitor.m */; };
2D3B5EC11D9B093900451313 /* RCTFPSGraph.m in Sources */ = {isa = PBXBuildFile; fileRef = 14F7A0EF1BDA714B003C6C10 /* RCTFPSGraph.m */; };
2D3B5EC21D9B093B00451313 /* RCTProfile.m in Sources */ = {isa = PBXBuildFile; fileRef = 1450FF811BCFF28A00208362 /* RCTProfile.m */; };
@ -235,7 +233,6 @@
3D302F641DF828F800D6DDAE /* RCTTiming.h in Headers */ = {isa = PBXBuildFile; fileRef = 13B07FED1A69327A00A75B9A /* RCTTiming.h */; };
3D302F651DF828F800D6DDAE /* RCTUIManager.h in Headers */ = {isa = PBXBuildFile; fileRef = 13E067481A70F434002CDEE1 /* RCTUIManager.h */; };
3D302F661DF828F800D6DDAE /* RCTFPSGraph.h in Headers */ = {isa = PBXBuildFile; fileRef = 14F7A0EE1BDA714B003C6C10 /* RCTFPSGraph.h */; };
3D302F671DF828F800D6DDAE /* RCTJSCProfiler.h in Headers */ = {isa = PBXBuildFile; fileRef = 14A43DF11C20B1C900794BC8 /* RCTJSCProfiler.h */; };
3D302F681DF828F800D6DDAE /* RCTMacros.h in Headers */ = {isa = PBXBuildFile; fileRef = 14BF71811C04795500C97D0C /* RCTMacros.h */; };
3D302F691DF828F800D6DDAE /* RCTProfile.h in Headers */ = {isa = PBXBuildFile; fileRef = 1450FF801BCFF28A00208362 /* RCTProfile.h */; };
3D302F6A1DF828F800D6DDAE /* RCTActivityIndicatorView.h in Headers */ = {isa = PBXBuildFile; fileRef = B95154301D1B34B200FE7B80 /* RCTActivityIndicatorView.h */; };
@ -344,7 +341,6 @@
3D302FE01DF8290600D6DDAE /* RCTTiming.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 13B07FED1A69327A00A75B9A /* RCTTiming.h */; };
3D302FE11DF8290600D6DDAE /* RCTUIManager.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 13E067481A70F434002CDEE1 /* RCTUIManager.h */; };
3D302FE21DF8290600D6DDAE /* RCTFPSGraph.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 14F7A0EE1BDA714B003C6C10 /* RCTFPSGraph.h */; };
3D302FE31DF8290600D6DDAE /* RCTJSCProfiler.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 14A43DF11C20B1C900794BC8 /* RCTJSCProfiler.h */; };
3D302FE41DF8290600D6DDAE /* RCTMacros.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 14BF71811C04795500C97D0C /* RCTMacros.h */; };
3D302FE51DF8290600D6DDAE /* RCTProfile.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 1450FF801BCFF28A00208362 /* RCTProfile.h */; };
3D302FE61DF8290600D6DDAE /* RCTActivityIndicatorView.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = B95154301D1B34B200FE7B80 /* RCTActivityIndicatorView.h */; };
@ -493,7 +489,6 @@
3D80D95F1DF6FA890028D040 /* RCTTiming.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 13B07FED1A69327A00A75B9A /* RCTTiming.h */; };
3D80D9601DF6FA890028D040 /* RCTUIManager.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 13E067481A70F434002CDEE1 /* RCTUIManager.h */; };
3D80D9611DF6FA890028D040 /* RCTFPSGraph.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 14F7A0EE1BDA714B003C6C10 /* RCTFPSGraph.h */; };
3D80D9621DF6FA890028D040 /* RCTJSCProfiler.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 14A43DF11C20B1C900794BC8 /* RCTJSCProfiler.h */; };
3D80D9631DF6FA890028D040 /* RCTMacros.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 14BF71811C04795500C97D0C /* RCTMacros.h */; };
3D80D9641DF6FA890028D040 /* RCTProfile.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 1450FF801BCFF28A00208362 /* RCTProfile.h */; };
3D80D9651DF6FA890028D040 /* RCTActivityIndicatorView.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = B95154301D1B34B200FE7B80 /* RCTActivityIndicatorView.h */; };
@ -610,7 +605,6 @@
3D80DA591DF820620028D040 /* RCTTiming.h in Headers */ = {isa = PBXBuildFile; fileRef = 13B07FED1A69327A00A75B9A /* RCTTiming.h */; };
3D80DA5A1DF820620028D040 /* RCTUIManager.h in Headers */ = {isa = PBXBuildFile; fileRef = 13E067481A70F434002CDEE1 /* RCTUIManager.h */; };
3D80DA5B1DF820620028D040 /* RCTFPSGraph.h in Headers */ = {isa = PBXBuildFile; fileRef = 14F7A0EE1BDA714B003C6C10 /* RCTFPSGraph.h */; };
3D80DA5C1DF820620028D040 /* RCTJSCProfiler.h in Headers */ = {isa = PBXBuildFile; fileRef = 14A43DF11C20B1C900794BC8 /* RCTJSCProfiler.h */; };
3D80DA5D1DF820620028D040 /* RCTMacros.h in Headers */ = {isa = PBXBuildFile; fileRef = 14BF71811C04795500C97D0C /* RCTMacros.h */; };
3D80DA5E1DF820620028D040 /* RCTProfile.h in Headers */ = {isa = PBXBuildFile; fileRef = 1450FF801BCFF28A00208362 /* RCTProfile.h */; };
3D80DA5F1DF820620028D040 /* RCTActivityIndicatorView.h in Headers */ = {isa = PBXBuildFile; fileRef = B95154301D1B34B200FE7B80 /* RCTActivityIndicatorView.h */; };
@ -899,7 +893,6 @@
3D302FE01DF8290600D6DDAE /* RCTTiming.h in Copy Headers */,
3D302FE11DF8290600D6DDAE /* RCTUIManager.h in Copy Headers */,
3D302FE21DF8290600D6DDAE /* RCTFPSGraph.h in Copy Headers */,
3D302FE31DF8290600D6DDAE /* RCTJSCProfiler.h in Copy Headers */,
3D302FE41DF8290600D6DDAE /* RCTMacros.h in Copy Headers */,
3D302FE51DF8290600D6DDAE /* RCTProfile.h in Copy Headers */,
3D302FE61DF8290600D6DDAE /* RCTActivityIndicatorView.h in Copy Headers */,
@ -1059,7 +1052,6 @@
3D80D95F1DF6FA890028D040 /* RCTTiming.h in Copy Headers */,
3D80D9601DF6FA890028D040 /* RCTUIManager.h in Copy Headers */,
3D80D9611DF6FA890028D040 /* RCTFPSGraph.h in Copy Headers */,
3D80D9621DF6FA890028D040 /* RCTJSCProfiler.h in Copy Headers */,
3D80D9631DF6FA890028D040 /* RCTMacros.h in Copy Headers */,
3D80D9641DF6FA890028D040 /* RCTProfile.h in Copy Headers */,
3D80D9651DF6FA890028D040 /* RCTActivityIndicatorView.h in Copy Headers */,
@ -1279,8 +1271,6 @@
1450FF851BCFF28A00208362 /* RCTProfileTrampoline-x86_64.S */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.asm; path = "RCTProfileTrampoline-x86_64.S"; sourceTree = "<group>"; };
1482F9E61B55B927000ADFF3 /* RCTBridgeDelegate.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = RCTBridgeDelegate.h; sourceTree = "<group>"; };
14A43DB81C1F849600794BC8 /* RCTBridge+Private.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "RCTBridge+Private.h"; sourceTree = "<group>"; };
14A43DF11C20B1C900794BC8 /* RCTJSCProfiler.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTJSCProfiler.h; sourceTree = "<group>"; };
14A43DF21C20B1C900794BC8 /* RCTJSCProfiler.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTJSCProfiler.m; sourceTree = "<group>"; };
14BF717F1C04793D00C97D0C /* RCTProfileTrampoline-i386.S */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.asm; path = "RCTProfileTrampoline-i386.S"; sourceTree = "<group>"; };
14BF71811C04795500C97D0C /* RCTMacros.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTMacros.h; sourceTree = "<group>"; };
14C2CA6F1B3AC63800E6CBB2 /* RCTModuleMethod.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTModuleMethod.h; sourceTree = "<group>"; };
@ -1633,8 +1623,6 @@
children = (
14F7A0EE1BDA714B003C6C10 /* RCTFPSGraph.h */,
14F7A0EF1BDA714B003C6C10 /* RCTFPSGraph.m */,
14A43DF11C20B1C900794BC8 /* RCTJSCProfiler.h */,
14A43DF21C20B1C900794BC8 /* RCTJSCProfiler.m */,
14BF71811C04795500C97D0C /* RCTMacros.h */,
14F7A0EB1BDA3B3C003C6C10 /* RCTPerfMonitor.m */,
1450FF801BCFF28A00208362 /* RCTProfile.h */,
@ -1965,7 +1953,6 @@
3D302F641DF828F800D6DDAE /* RCTTiming.h in Headers */,
3D302F651DF828F800D6DDAE /* RCTUIManager.h in Headers */,
3D302F661DF828F800D6DDAE /* RCTFPSGraph.h in Headers */,
3D302F671DF828F800D6DDAE /* RCTJSCProfiler.h in Headers */,
3D302F681DF828F800D6DDAE /* RCTMacros.h in Headers */,
3D302F691DF828F800D6DDAE /* RCTProfile.h in Headers */,
3D302F6A1DF828F800D6DDAE /* RCTActivityIndicatorView.h in Headers */,
@ -2157,7 +2144,6 @@
3D80DA591DF820620028D040 /* RCTTiming.h in Headers */,
3D80DA5A1DF820620028D040 /* RCTUIManager.h in Headers */,
3D80DA5B1DF820620028D040 /* RCTFPSGraph.h in Headers */,
3D80DA5C1DF820620028D040 /* RCTJSCProfiler.h in Headers */,
A12E9E2B1E5DEB860029001B /* RCTSRWebSocket.h in Headers */,
3D80DA5D1DF820620028D040 /* RCTMacros.h in Headers */,
3D80DA5E1DF820620028D040 /* RCTProfile.h in Headers */,
@ -2489,7 +2475,6 @@
2D3B5EC91D9B095C00451313 /* RCTBorderDrawing.m in Sources */,
B50558411E43E13D00F71A00 /* RCTDevMenu.m in Sources */,
2D3B5E991D9B089A00451313 /* RCTDisplayLink.m in Sources */,
2D3B5EBF1D9B093300451313 /* RCTJSCProfiler.m in Sources */,
2D3B5EA11D9B08B600451313 /* RCTModuleData.mm in Sources */,
2D3B5EEA1D9B09CD00451313 /* RCTTabBar.m in Sources */,
3D7BFCEA1EA8E1F4008DFB7A /* RCTPackagerConnection.m in Sources */,
@ -2645,7 +2630,6 @@
597AD1BF1E577D7800152581 /* RCTRootContentView.m in Sources */,
13723B501A82FD3C00F88898 /* RCTStatusBarManager.m in Sources */,
000E6CEB1AB0E980000CDF4D /* RCTSourceCode.m in Sources */,
14A43DF31C20B1C900794BC8 /* RCTJSCProfiler.m in Sources */,
001BFCD01D8381DE008E587E /* RCTMultipartStreamReader.m in Sources */,
133CAE8E1B8E5CFD00F6AD92 /* RCTDatePicker.m in Sources */,
14C2CA761B3AC64F00E6CBB2 /* RCTFrameUpdate.m in Sources */,

View File

@ -88,10 +88,6 @@ public interface CatalystInstance
*/
void removeBridgeIdleDebugListener(NotThreadSafeBridgeIdleDebugListener listener);
boolean supportsProfiling();
void startProfiler(String title);
void stopProfiler(String title, String filename);
@VisibleForTesting
void setGlobalVariable(String propName, String jsonValue);

View File

@ -429,17 +429,6 @@ public class CatalystInstanceImpl implements CatalystInstance {
@Override
public native long getJavaScriptContext();
// TODO mhorowitz: add mDestroyed checks to the next three methods
@Override
public native boolean supportsProfiling();
@Override
public native void startProfiler(String title);
@Override
public native void stopProfiler(String title, String filename);
private void incrementPendingJSCalls() {
int oldPendingCalls = mPendingJSCalls.getAndIncrement();
boolean wasIdle = oldPendingCalls == 0;

View File

@ -104,9 +104,6 @@ void CatalystInstanceImpl::registerNatives() {
makeNativeMethod("setGlobalVariable", CatalystInstanceImpl::setGlobalVariable),
makeNativeMethod("getJavaScriptContext", CatalystInstanceImpl::getJavaScriptContext),
makeNativeMethod("jniHandleMemoryPressure", CatalystInstanceImpl::handleMemoryPressure),
makeNativeMethod("supportsProfiling", CatalystInstanceImpl::supportsProfiling),
makeNativeMethod("startProfiler", CatalystInstanceImpl::startProfiler),
makeNativeMethod("stopProfiler", CatalystInstanceImpl::stopProfiler),
});
JNativeRunnable::registerNatives();
@ -266,25 +263,4 @@ void CatalystInstanceImpl::handleMemoryPressure(int pressureLevel) {
#endif
}
jboolean CatalystInstanceImpl::supportsProfiling() {
if (!instance_) {
return false;
}
return instance_->supportsProfiling();
}
void CatalystInstanceImpl::startProfiler(const std::string& title) {
if (!instance_) {
return;
}
return instance_->startProfiler(title);
}
void CatalystInstanceImpl::stopProfiler(const std::string& title, const std::string& filename) {
if (!instance_) {
return;
}
return instance_->stopProfiler(title, filename);
}
}}

View File

@ -69,9 +69,6 @@ class CatalystInstanceImpl : public jni::HybridClass<CatalystInstanceImpl> {
std::string&& jsonValue);
jlong getJavaScriptContext();
void handleMemoryPressure(int pressureLevel);
jboolean supportsProfiling();
void startProfiler(const std::string& title);
void stopProfiler(const std::string& title, const std::string& filename);
// This should be the only long-lived strong reference, but every C++ class
// will have a weak reference.

View File

@ -10,7 +10,6 @@ LOCAL_SRC_FILES := \
JSCExecutor.cpp \
JSBigString.cpp \
JSBundleType.cpp \
JSCLegacyProfiler.cpp \
JSCLegacyTracing.cpp \
JSCMemory.cpp \
JSCNativeModules.cpp \

View File

@ -100,18 +100,6 @@ void Instance::loadUnbundle(std::unique_ptr<JSModulesUnbundle> unbundle,
loadApplication(std::move(unbundle), std::move(startupScript),
std::move(startupScriptSourceURL));
}
}
bool Instance::supportsProfiling() {
return nativeToJsBridge_->supportsProfiling();
}
void Instance::startProfiler(const std::string& title) {
return nativeToJsBridge_->startProfiler(title);
}
void Instance::stopProfiler(const std::string& title, const std::string& filename) {
return nativeToJsBridge_->stopProfiler(title, filename);
}
void Instance::setGlobalVariable(std::string propName,

View File

@ -53,8 +53,6 @@ class RN_EXPORT Instance {
std::string startupScriptSourceURL,
bool loadSynchronously);
bool supportsProfiling();
void startProfiler(const std::string& title);
void stopProfiler(const std::string& title, const std::string& filename);
void setGlobalVariable(std::string propName, std::unique_ptr<const JSBigString> jsonValue);
void *getJavaScriptContext();
void callJSFunction(std::string&& module, std::string&& method, folly::dynamic&& params);

View File

@ -39,7 +39,6 @@
#endif
#ifdef WITH_JSC_EXTRA_TRACING
#include "JSCLegacyProfiler.h"
#include "JSCLegacyTracing.h"
#endif
@ -240,7 +239,6 @@ void JSCExecutor::initOnJSVMThread() throw(JSException) {
#endif
#ifdef WITH_JSC_EXTRA_TRACING
addNativeProfilingHooks(m_context);
addNativeTracingLegacyHooks(m_context);
#endif
@ -554,32 +552,6 @@ void* JSCExecutor::getJavaScriptContext() {
return m_context;
}
bool JSCExecutor::supportsProfiling() {
#ifdef WITH_FBSYSTRACE
return true;
#else
return false;
#endif
}
void JSCExecutor::startProfiler(const std::string &titleString) {
#ifdef WITH_JSC_EXTRA_TRACING
String title(m_context, titleString.c_str());
#if WITH_REACT_INTERNAL_SETTINGS
JSStartProfiling(m_context, title, false);
#else
JSStartProfiling(m_context, title);
#endif
#endif
}
void JSCExecutor::stopProfiler(const std::string &titleString, const std::string& filename) {
#ifdef WITH_JSC_EXTRA_TRACING
String title(m_context, titleString.c_str());
facebook::react::stopAndOutputProfilingFile(m_context, title, filename.c_str());
#endif
}
#ifdef WITH_JSC_MEMORY_PRESSURE
void JSCExecutor::handleMemoryPressure(int pressureLevel) {
JSHandleMemoryPressure(this, m_context, static_cast<JSMemoryPressure>(pressureLevel));

View File

@ -79,10 +79,6 @@ public:
virtual void* getJavaScriptContext() override;
virtual bool supportsProfiling() override;
virtual void startProfiler(const std::string &titleString) override;
virtual void stopProfiler(const std::string &titleString, const std::string &filename) override;
#ifdef WITH_JSC_MEMORY_PRESSURE
virtual void handleMemoryPressure(int pressureLevel) override;
#endif

View File

@ -1,89 +0,0 @@
// Copyright 2004-present Facebook. All Rights Reserved.
#ifdef WITH_JSC_EXTRA_TRACING
#include <stdio.h>
#include <string.h>
#include <JavaScriptCore/API/JSProfilerPrivate.h>
#include <jsc_legacy_profiler.h>
#include <jschelpers/JavaScriptCore.h>
#include <jschelpers/JSCHelpers.h>
#include <jschelpers/Value.h>
#include "JSCLegacyProfiler.h"
using namespace facebook::react;
static JSValueRef nativeProfilerStart(
JSContextRef ctx,
JSObjectRef function,
JSObjectRef thisObject,
size_t argumentCount,
const JSValueRef arguments[],
JSValueRef* exception) {
if (argumentCount < 1) {
if (exception) {
*exception = Value::makeError(
ctx,
"nativeProfilerStart: requires at least 1 argument");
}
return Value::makeUndefined(ctx);
}
auto title = String::adopt(ctx, JSValueToStringCopy(ctx, arguments[0], exception));
#if WITH_REACT_INTERNAL_SETTINGS
JSStartProfiling(ctx, title, false);
#else
JSStartProfiling(ctx, title);
#endif
return Value::makeUndefined(ctx);
}
static JSValueRef nativeProfilerEnd(
JSContextRef ctx,
JSObjectRef function,
JSObjectRef thisObject,
size_t argumentCount,
const JSValueRef arguments[],
JSValueRef* exception) {
if (argumentCount < 1) {
if (exception) {
*exception = Value::makeError(
ctx,
"nativeProfilerEnd: requires at least 1 argument");
}
return Value::makeUndefined(ctx);
}
std::string writeLocation("/sdcard/");
if (argumentCount > 1) {
auto fileName = String::adopt(
ctx, JSC_JSValueToStringCopy(ctx, arguments[1], exception));
writeLocation += fileName.str();
} else {
writeLocation += "profile.json";
}
auto title = String::adopt(
ctx, JSC_JSValueToStringCopy(ctx, arguments[0], exception));
JSEndProfilingAndRender(ctx, title, writeLocation.c_str());
return Value::makeUndefined(ctx);
}
namespace facebook {
namespace react {
void stopAndOutputProfilingFile(
JSContextRef ctx,
JSStringRef title,
const char *filename) {
JSEndProfilingAndRender(ctx, title, filename);
}
void addNativeProfilingHooks(JSGlobalContextRef ctx) {
// JSEnableByteCodeProfiling();
installGlobalFunction(ctx, "nativeProfilerStart", nativeProfilerStart);
installGlobalFunction(ctx, "nativeProfilerEnd", nativeProfilerEnd);
}
} }
#endif

View File

@ -1,20 +0,0 @@
// Copyright 2004-present Facebook. All Rights Reserved.
#pragma once
#ifdef WITH_JSC_EXTRA_TRACING
#include <jschelpers/JavaScriptCore.h>
namespace facebook {
namespace react {
void addNativeProfilingHooks(JSGlobalContextRef ctx);
void stopAndOutputProfilingFile(
JSContextRef ctx,
JSStringRef title,
const char *filename);
} }
#endif

View File

@ -72,11 +72,6 @@ public:
virtual void* getJavaScriptContext() {
return nullptr;
}
virtual bool supportsProfiling() {
return false;
}
virtual void startProfiler(const std::string &titleString) {}
virtual void stopProfiler(const std::string &titleString, const std::string &filename) {}
#ifdef WITH_JSC_MEMORY_PRESSURE
virtual void handleMemoryPressure(int pressureLevel) {}

View File

@ -184,23 +184,6 @@ void* NativeToJsBridge::getJavaScriptContext() {
return m_executor->getJavaScriptContext();
}
bool NativeToJsBridge::supportsProfiling() {
// Intentionally doesn't post to jsqueue. supportsProfiling() can be called from any thread.
return m_executor->supportsProfiling();
}
void NativeToJsBridge::startProfiler(const std::string& title) {
runOnExecutorQueue([=] (JSExecutor* executor) {
executor->startProfiler(title);
});
}
void NativeToJsBridge::stopProfiler(const std::string& title, const std::string& filename) {
runOnExecutorQueue([=] (JSExecutor* executor) {
executor->stopProfiler(title, filename);
});
}
#ifdef WITH_JSC_MEMORY_PRESSURE
void NativeToJsBridge::handleMemoryPressure(int pressureLevel) {
runOnExecutorQueue([=] (JSExecutor* executor) {

View File

@ -100,9 +100,6 @@ public:
void setGlobalVariable(std::string propName, std::unique_ptr<const JSBigString> jsonValue);
void* getJavaScriptContext();
bool supportsProfiling();
void startProfiler(const std::string& title);
void stopProfiler(const std::string& title, const std::string& filename);
#ifdef WITH_JSC_MEMORY_PRESSURE
void handleMemoryPressure(int pressureLevel);

View File

@ -1,48 +0,0 @@
/**
* Copyright (c) 2015-present, Facebook, Inc.
* All rights reserved.
*
* This source code is licensed under the BSD-style license found in the
* LICENSE file in the root directory of this source tree. An additional grant
* of patent rights can be found in the PATENTS file in the same directory.
*/
'use strict';
const execFile = require('child_process').execFile;
const fs = require('fs');
const path = require('path');
module.exports = function(req, res, next) {
if (req.url !== '/cpu-profile') {
next();
return;
}
console.log('Dumping CPU profile information...');
var dumpName = '/tmp/cpu-profile_' + Date.now();
fs.writeFileSync(dumpName + '.json', req.rawBody);
var cmdPath = path.join(
__dirname,
'../../../JSCLegacyProfiler/json2trace'
);
execFile(
cmdPath,
[
'-cpuprofiler',
dumpName + '.cpuprofile',
dumpName + '.json',
],
function(error) {
if (error) {
console.error(error);
res.end('Unknown error: ' + error.message);
} else {
var response = 'Your profile was generated at\n\n' + dumpName + '.cpuprofile\n\n' +
'Open `Chrome Dev Tools > Profiles > Load` and select the profile to visualize it.';
console.log(response);
res.end(response);
}
}
);
};

View File

@ -19,7 +19,6 @@ const Terminal = require('metro-bundler/src/lib/Terminal');
const attachHMRServer = require('./util/attachHMRServer');
const connect = require('connect');
const copyToClipBoardMiddleware = require('./middleware/copyToClipBoardMiddleware');
const cpuProfilerMiddleware = require('./middleware/cpuProfilerMiddleware');
const defaultAssetExts = require('metro-bundler/src/defaults').assetExts;
const defaultSourceExts = require('metro-bundler/src/defaults').sourceExts;
const defaultPlatforms = require('metro-bundler/src/defaults').platforms;
@ -78,7 +77,6 @@ function runServer(
.use(copyToClipBoardMiddleware)
.use(statusPageMiddleware)
.use(systraceProfileMiddleware)
.use(cpuProfilerMiddleware)
.use(indexPageMiddleware)
.use(packagerServer.processRequest.bind(packagerServer));