Skip to content

Commit

Permalink
Version 3.6.0-251.0.dev
Browse files Browse the repository at this point in the history
Merge 8f89bbe into dev
  • Loading branch information
Dart CI committed Sep 13, 2024
2 parents 397309e + 8f89bbe commit eb66430
Show file tree
Hide file tree
Showing 4 changed files with 80 additions and 34 deletions.
22 changes: 12 additions & 10 deletions pkg/vm/lib/modular/transformations/ffi/use_sites.dart
Original file line number Diff line number Diff line change
Expand Up @@ -1481,11 +1481,10 @@ mixin _FfiUseSiteTransformer on FfiTransformer {
parent.addProcedure(newTarget);
}
}

return StaticInvocation(
newTarget,
Arguments(newArguments),
);
)..parent = parent;
}

/// Converts a single parameter with argument for [_replaceNativeCall].
Expand All @@ -1510,16 +1509,19 @@ mixin _FfiUseSiteTransformer on FfiTransformer {
return ('', parameterType, argument);
}

// If an argument is an invalid expression, ffi don't need to report
// any error further, so skipping transformation for its descendants of the
// argument by transforming into empty expression (which is invalid)
if ((argument is AsExpression && argument.operand is InvalidExpression) ||
argument is InvalidExpression) {
return ('E', parameterType, InvalidExpression('Invalid Type'));
if (argument is InvalidExpression && argument.expression is AsExpression) {
final parent = argument.expression as AsExpression;
final (_, _, transformedArgument) =
_replaceNativeCallParameterAndArgument(
parameter, parameterType, parent.operand, fileOffset);
return (
'E',
parameterType,
InvalidExpression('Invalid Type', transformedArgument)
);
}
if (argument is InstanceInvocation &&
argument.interfaceTarget == castMethod &&
argument.functionType.returnType == parameterType) {
argument.interfaceTarget == castMethod) {
// Argument is .address.cast(), so truncating .cast()
final subExpression = argument.receiver;
return _replaceNativeCallParameterAndArgument(
Expand Down
18 changes: 10 additions & 8 deletions runtime/vm/compiler/backend/il_x64.cc
Original file line number Diff line number Diff line change
Expand Up @@ -2057,9 +2057,11 @@ LocationSummary* StoreIndexedInstr::MakeLocationSummary(Zone* zone,
RepresentationUtils::RepresentationOfArrayElement(class_id());
if (RepresentationUtils::IsUnboxedInteger(rep)) {
if (rep == kUnboxedUint8 || rep == kUnboxedInt8) {
// TODO(fschneider): Add location constraint for byte registers (RAX,
// RBX, RCX, RDX) instead of using a fixed register.
locs->set_in(2, LocationFixedRegisterOrSmiConstant(value(), RAX));
if (IsClampedTypedDataBaseClassId(class_id())) {
locs->set_in(2, LocationWritableRegisterOrSmiConstant(value()));
} else {
locs->set_in(2, LocationRegisterOrSmiConstant(value()));
}
} else {
locs->set_in(2, Location::RequiresRegister());
}
Expand Down Expand Up @@ -2128,18 +2130,18 @@ void StoreIndexedInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
}
__ movb(element_address, compiler::Immediate(static_cast<int8_t>(value)));
} else {
const Register storedValueReg = locs()->in(2).reg();
const Register value = locs()->in(2).reg();
compiler::Label store_value, store_0xff;
__ CompareImmediate(storedValueReg, compiler::Immediate(0xFF));
__ CompareImmediate(value, compiler::Immediate(0xFF));
__ j(BELOW_EQUAL, &store_value, compiler::Assembler::kNearJump);
// Clamp to 0x0 or 0xFF respectively.
__ j(GREATER, &store_0xff);
__ xorq(storedValueReg, storedValueReg);
__ xorq(value, value);
__ jmp(&store_value, compiler::Assembler::kNearJump);
__ Bind(&store_0xff);
__ LoadImmediate(storedValueReg, compiler::Immediate(0xFF));
__ LoadImmediate(value, compiler::Immediate(0xFF));
__ Bind(&store_value);
__ movb(element_address, ByteRegisterOf(storedValueReg));
__ movb(element_address, ByteRegisterOf(value));
}
} else if (RepresentationUtils::IsUnboxedInteger(rep)) {
if (rep == kUnboxedUint8 || rep == kUnboxedInt8) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,9 @@
import 'dart:ffi';
import 'dart:typed_data';

@Native<Void Function(Pointer<Void>)>()
external void myNonLeafNative(Pointer<Void> buff);

@Native<Void Function(Pointer<Void>, Pointer<Int8>)>(isLeaf: true)
external void myNativeWith2Param(Pointer<Void> buffer, Pointer<Int8> buffer2);

Expand All @@ -13,7 +16,7 @@ external void myNativeWith2Param(Pointer<Void> buffer, Pointer<Int8> buffer2);
external void myNativeWith3Param(
Pointer<Void> buffer, Pointer<Int8> buffer2, Pointer<Void> buffer3);

void test_wrong_type() {
void testDefinedLeaf() {
final buffer = Int8List.fromList([1]);
myNativeWith2Param(buffer.address, buffer.address);
// ^^^^^^^
Expand Down Expand Up @@ -105,30 +108,69 @@ void test_wrong_type() {
// [analyzer] COMPILE_TIME_ERROR.ARGUMENT_TYPE_NOT_ASSIGNABLE
}

void test_undefined_arguments() {
void testUndefinedLeaf() {
final buffer = Int8List.fromList([1]);
myNativeWith2Param(buffer.address.cast(), buffer.address.cd);
// ^^
// [cfe] The getter 'cd' isn't defined for the class 'Pointer<Int8>'.
myNativeWith2Param(buffer.address.cast(), buffer.address.doesntExist);
// ^^^^^^^^^^^
// [cfe] The getter 'doesntExist' isn't defined for the class 'Pointer<Int8>'.
// [analyzer] COMPILE_TIME_ERROR.UNDEFINED_GETTER
// ^^^^^^^
// [cfe] The '.address' expression can only be used as argument to a leaf native external call.
// [analyzer] COMPILE_TIME_ERROR.ADDRESS_POSITION

// This address position error is not expected which is a bug,
// https://github.com/dart-lang/sdk/issues/56613

myNativeWith2Param(buffer.address.cast<Int8>().cd, buffer.address);
// ^^
// [cfe] The getter 'cd' isn't defined for the class 'Pointer<Int8>'.
myNativeWith2Param(buffer.address.cast<Int8>().doesntExist, buffer.address);
// ^^^^^^^^^^^
// [cfe] The getter 'doesntExist' isn't defined for the class 'Pointer<Int8>'.
// [analyzer] COMPILE_TIME_ERROR.UNDEFINED_GETTER
// ^^^^^^^
// [cfe] The '.address' expression can only be used as argument to a leaf native external call.
// [analyzer] COMPILE_TIME_ERROR.ADDRESS_POSITION
}

void testUndefinedNonLeaf() {
final buffer = Int8List.fromList([1]);

myNonLeafNative(buffer.address.cast().doesntExist);
// ^^^^^^^^^^^
// [analyzer] COMPILE_TIME_ERROR.UNDEFINED_GETTER
// [cfe] The getter 'doesntExist' isn't defined for the class 'Pointer<NativeType>'.
// ^^^^^^^
// [analyzer] COMPILE_TIME_ERROR.ADDRESS_POSITION
// [cfe] The '.address' expression can only be used as argument to a leaf native external call.
myNonLeafNative(buffer.address.doesntExist);
// ^^^^^^^^^^^
// [analyzer] COMPILE_TIME_ERROR.UNDEFINED_GETTER
// [cfe] The getter 'doesntExist' isn't defined for the class 'Pointer<Int8>'.
// ^^^^^^^
// [analyzer] COMPILE_TIME_ERROR.ADDRESS_POSITION
// [cfe] The '.address' expression can only be used as argument to a leaf native external call.
}

// This address position error is not expected which is a bug,
// https://github.com/dart-lang/sdk/issues/56613
void testDefinedNonLeaf() {
final buffer = Int8List.fromList([1]);
myNonLeafNative(buffer.address.cast().address);
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
// [analyzer] COMPILE_TIME_ERROR.ARGUMENT_TYPE_NOT_ASSIGNABLE
// ^^^^^^^
// [cfe] The argument type 'int' can't be assigned to the parameter type 'Pointer<Void>'.
// ^^^^^^^
// [analyzer] COMPILE_TIME_ERROR.ADDRESS_POSITION
// [cfe] The '.address' expression can only be used as argument to a leaf native external call.

myNonLeafNative(buffer.address.address);
// ^^^^^^^^^^^^^^^^^^^^^^
// [analyzer] COMPILE_TIME_ERROR.ARGUMENT_TYPE_NOT_ASSIGNABLE
// ^^^^^^^
// [cfe] The argument type 'int' can't be assigned to the parameter type 'Pointer<Void>'.
// ^^^^^^^
// [analyzer] COMPILE_TIME_ERROR.ADDRESS_POSITION
// [cfe] The '.address' expression can only be used as argument to a leaf native external call.
}

void main() {
test_undefined_arguments();
test_wrong_type();
testDefinedLeaf();
testDefinedNonLeaf();

testUndefinedLeaf();
testUndefinedNonLeaf();
}
2 changes: 1 addition & 1 deletion tools/VERSION
Original file line number Diff line number Diff line change
Expand Up @@ -27,5 +27,5 @@ CHANNEL dev
MAJOR 3
MINOR 6
PATCH 0
PRERELEASE 250
PRERELEASE 251
PRERELEASE_PATCH 0

0 comments on commit eb66430

Please sign in to comment.