|
|
920 |
case "Drf": |
920 |
case "Drf": |
921 |
var variable = null; |
921 |
var variable = null; |
922 |
if (lhs.Exp[0].Kind == "Var") { |
922 |
if (lhs.Exp[0].Kind == "Var") { |
923 |
variable = lhs.Exp[0].Variable; |
923 |
variable = lhs.Exp[0].Variable; |
924 |
if (isSafeVariable(entry, variable)) |
924 |
if (isSafeVariable(entry, variable)) |
925 |
return; |
925 |
return; |
926 |
} else if (lhs.Exp[0].Kind == "Fld") { |
926 |
} else if (lhs.Exp[0].Kind == "Fld") { |
927 |
const { |
927 |
const { |
|
|
928 |
Name: [ fieldName ], |
928 |
Type: {Kind, Type: fieldType}, |
929 |
Type: {Kind, Type: fieldType}, |
929 |
FieldCSU: {Type: {Kind: containerTypeKind, |
930 |
FieldCSU: {Type: {Kind: containerTypeKind, |
930 |
Name: containerTypeName}} |
931 |
Name: containerTypeName}} |
931 |
} = lhs.Exp[0].Field; |
932 |
} = lhs.Exp[0].Field; |
932 |
const [containerExpr] = lhs.Exp[0].Exp; |
933 |
const [containerExpr] = lhs.Exp[0].Exp; |
933 |
|
934 |
|
934 |
if (containerTypeKind == 'CSU' && |
935 |
if (containerTypeKind == 'CSU' && |
935 |
Kind == 'Pointer' && |
936 |
Kind == 'Pointer' && |
936 |
isEdgeSafeArgument(entry, containerExpr) && |
937 |
isEdgeSafeArgument(entry, containerExpr) && |
937 |
isSafeMemberPointer(containerTypeName, fieldType)) |
938 |
isSafeMemberPointer(containerTypeName, fieldName, fieldType)) |
938 |
{ |
939 |
{ |
939 |
return; |
940 |
return; |
940 |
} |
941 |
} |
941 |
|
|
|
942 |
} |
942 |
} |
943 |
if (fields.length) |
943 |
if (fields.length) |
944 |
checkFieldWrite(entry, location, fields); |
944 |
checkFieldWrite(entry, location, fields); |
945 |
else |
945 |
else |
946 |
checkDereferenceWrite(entry, location, variableName(variable)); |
946 |
checkDereferenceWrite(entry, location, variableName(variable)); |
947 |
return; |
947 |
return; |
948 |
case "Int": |
948 |
case "Int": |
949 |
if (isZero(lhs)) { |
949 |
if (isZero(lhs)) { |
|
1350 |
// If it is initialized at this point we should have seen *some* write |
1350 |
// If it is initialized at this point we should have seen *some* write |
1351 |
// already, since the CFG edges are visited in reverse post order. |
1351 |
// already, since the CFG edges are visited in reverse post order. |
1352 |
if (name in assignments) |
1352 |
if (name in assignments) |
1353 |
return false; |
1353 |
return false; |
1354 |
|
1354 |
|
1355 |
return true; |
1355 |
return true; |
1356 |
} |
1356 |
} |
1357 |
|
1357 |
|
1358 |
function isSafeMemberPointer(containerType, memberType) |
1358 |
function isSafeMemberPointer(containerType, memberName, memberType) |
1359 |
{ |
1359 |
{ |
|
|
1360 |
// nsTArray owns its header. |
1361 |
if (containerType.includes("nsTArray_base") && memberName == "mHdr") |
1362 |
return true; |
1363 |
|
1360 |
if (memberType.Kind != 'Pointer') |
1364 |
if (memberType.Kind != 'Pointer') |
1361 |
return false; |
1365 |
return false; |
1362 |
|
1366 |
|
1363 |
// Special-cases go here :) |
1367 |
// Special-cases go here :) |
1364 |
return false; |
1368 |
return false; |
1365 |
} |
1369 |
} |
1366 |
|
1370 |
|
1367 |
// Return whether 'exp == value' holds only when execution is on the main thread. |
1371 |
// Return whether 'exp == value' holds only when execution is on the main thread. |