mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
Bug 934698 - Suppress nsISupports.{AddRef,Release} when called directly, r=bhackett
DONBUILD because NPOTB yet
This commit is contained in:
parent
632701b955
commit
c9c4a1d06f
@ -236,7 +236,9 @@ function edgeCanGC(edge)
|
||||
var field = callee.Exp[0].Field;
|
||||
var csuName = field.FieldCSU.Type.Name;
|
||||
var fullFieldName = csuName + "." + field.Name[0];
|
||||
return fieldCallCannotGC(csuName, fullFieldName) ? null : fullFieldName;
|
||||
if (fieldCallCannotGC(csuName, fullFieldName))
|
||||
return null;
|
||||
return (fullFieldName in suppressedFunctions) ? null : fullFieldName;
|
||||
}
|
||||
assert(callee.Exp[0].Kind == "Var");
|
||||
var calleeName = callee.Exp[0].Variable.Name[0];
|
||||
|
@ -69,8 +69,6 @@ var ignoreCallees = {
|
||||
"js::Class.trace" : true,
|
||||
"js::Class.finalize" : true,
|
||||
"JSRuntime.destroyPrincipals" : true,
|
||||
"nsISupports.AddRef" : true,
|
||||
"nsISupports.Release" : true, // makes me a bit nervous; this is a bug but can happen
|
||||
"nsIGlobalObject.GetGlobalJSObject" : true, // virtual but no implementation can GC
|
||||
"nsAXPCNativeCallContext.GetJSContext" : true,
|
||||
"js::jit::MDefinition.op" : true, // macro generated virtuals just return a constant
|
||||
|
@ -49,7 +49,7 @@ function processCSU(csuName, csu)
|
||||
}
|
||||
}
|
||||
|
||||
function findVirtualFunctions(csu, field)
|
||||
function findVirtualFunctions(csu, field, suppressed)
|
||||
{
|
||||
var worklist = [csu];
|
||||
|
||||
@ -60,8 +60,10 @@ function findVirtualFunctions(csu, field)
|
||||
while (worklist.length) {
|
||||
var csu = worklist.pop();
|
||||
if (csu == "nsISupports") {
|
||||
if (field == "AddRef" || field == "Release")
|
||||
if (field == "AddRef" || field == "Release") {
|
||||
suppressed[0] = true;
|
||||
return [];
|
||||
}
|
||||
return null;
|
||||
}
|
||||
if (csu in superclasses) {
|
||||
@ -132,8 +134,16 @@ function getCallees(edge)
|
||||
var fieldName = field.Name[0];
|
||||
var csuName = field.FieldCSU.Type.Name;
|
||||
var functions = null;
|
||||
if ("FieldInstanceFunction" in field)
|
||||
functions = findVirtualFunctions(csuName, fieldName);
|
||||
if ("FieldInstanceFunction" in field) {
|
||||
var suppressed = [ false ];
|
||||
functions = findVirtualFunctions(csuName, fieldName, suppressed);
|
||||
if (suppressed[0]) {
|
||||
// Field call known to not GC; mark it as suppressed so
|
||||
// direct invocations will be ignored
|
||||
callees.push({'kind': "field", 'csu': csuName, 'field': fieldName,
|
||||
'suppressed': true});
|
||||
}
|
||||
}
|
||||
if (functions) {
|
||||
// Known set of virtual call targets.
|
||||
for (var name of functions)
|
||||
@ -173,14 +183,15 @@ function processBody(caller, body)
|
||||
for (var edge of body.PEdge) {
|
||||
if (edge.Kind != "Call")
|
||||
continue;
|
||||
var suppressText = "";
|
||||
var edgeSuppressed = false;
|
||||
var seen = seenCallees;
|
||||
if (edge.Index[0] in body.suppressed) {
|
||||
suppressText = "SUPPRESS_GC ";
|
||||
edgeSuppressed = true;
|
||||
seen = seenSuppressedCallees;
|
||||
}
|
||||
var prologue = suppressText + memo(caller) + " ";
|
||||
for (var callee of getCallees(edge)) {
|
||||
var prologue = (edgeSuppressed || callee.suppressed) ? "SUPPRESS_GC " : "";
|
||||
prologue += memo(caller) + " ";
|
||||
if (callee.kind == 'direct') {
|
||||
if (!(callee.name in seen)) {
|
||||
seen[name] = true;
|
||||
|
@ -48,9 +48,11 @@ try:
|
||||
print >>refs, line
|
||||
continue
|
||||
|
||||
m = re.match(r"^Function.*has unrooted.*of type.*live across GC call '(.*?)'", line)
|
||||
m = re.match(r"^Function.*has unrooted.*of type.*live across GC call ('?)(.*?)('?) at \S+:\d+$", line)
|
||||
if m:
|
||||
current_gcFunction = m.group(1)
|
||||
# Function names are surrounded by single quotes. Field calls
|
||||
# are unquoted.
|
||||
current_gcFunction = m.group(2)
|
||||
hazardousGCFunctions.setdefault(current_gcFunction, []).append(line)
|
||||
hazardOrder.append((current_gcFunction, len(hazardousGCFunctions[current_gcFunction]) - 1))
|
||||
num_hazards += 1
|
||||
@ -84,7 +86,10 @@ try:
|
||||
|
||||
for gcFunction, index in hazardOrder:
|
||||
gcHazards = hazardousGCFunctions[gcFunction]
|
||||
print >>hazards, (gcHazards[index] + gcExplanations[gcFunction])
|
||||
if gcFunction in gcExplanations:
|
||||
print >>hazards, (gcHazards[index] + gcExplanations[gcFunction])
|
||||
else:
|
||||
print >>hazards, gcHazards[index]
|
||||
|
||||
except IOError as e:
|
||||
print 'Failed: %s' % str(e)
|
||||
|
@ -39,6 +39,8 @@ var functionNames = [""];
|
||||
|
||||
function loadCallgraph(file)
|
||||
{
|
||||
var suppressedFieldCalls = {};
|
||||
|
||||
var textLines = snarf(file).split('\n');
|
||||
for (var line of textLines) {
|
||||
var match;
|
||||
@ -62,7 +64,9 @@ function loadCallgraph(file)
|
||||
var caller = functionNames[match[1]];
|
||||
var csu = match[2];
|
||||
var fullfield = csu + "." + match[3];
|
||||
if (!fieldCallCannotGC(csu, fullfield) && !suppressed)
|
||||
if (suppressed)
|
||||
suppressedFieldCalls[fullfield] = true;
|
||||
else if (!fieldCallCannotGC(csu, fullfield))
|
||||
addGCFunction(caller, "FieldCall: " + fullfield);
|
||||
} else if (match = /^D (\d+) (\d+)/.exec(line)) {
|
||||
var caller = functionNames[match[1]];
|
||||
@ -100,6 +104,10 @@ function loadCallgraph(file)
|
||||
delete gcFunctions[name];
|
||||
}
|
||||
|
||||
for (var name in suppressedFieldCalls) {
|
||||
suppressedFunctions[name] = true;
|
||||
}
|
||||
|
||||
for (var gcName of [ 'jsgc.cpp:void Collect(JSRuntime*, uint8, int64, uint32, uint32)',
|
||||
'void js::MinorGC(JSRuntime*, uint32)' ])
|
||||
{
|
||||
|
Loading…
Reference in New Issue
Block a user