blob: f5bf1f675ee473d9ce9c8f88060229291253c2c5 [file] [log] [blame]
// Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.
import 'dart:async';
import 'class.dart';
import 'instance.dart';
import 'library.dart';
import 'object.dart';
import 'scope.dart';
import 'source_location.dart';
VMFieldRef newVMFieldRef(Scope scope, Map json) {
if (json == null) return null;
assert(json["type"] == "@Field" || json["type"] == "Field");
return new VMFieldRef._(scope, json);
}
/// A reference to a field or variable.
class VMFieldRef implements VMObjectRef {
final Scope _scope;
/// The ID for this field, which is unique relative to its isolate.
final String _id;
/// Whether [_id] is guaranteed to be the same for different VM service field
/// objects that refer to the same field.
final bool _fixedId;
Uri get observatoryUrl => _scope.observatoryUrlFor(_id);
/// The name of this field.
final String name;
/// The owner of this field.
///
/// This is either a [VMLibraryRef] or a [VMClassRef].
final VMObjectRef owner;
/// The declared type of this field.
final VMTypeLikeInstanceRef declaredType;
/// Whether this is a const field.
final bool isConst;
/// Whether this is a final field.
final bool isFinal;
/// Whether this is a static field.
final bool isStatic;
/// The Dart declaration of this field, excluding its value.
String get description {
var buffer = new StringBuffer();
if (isStatic && owner is! VMLibraryRef) buffer.write("static ");
if (isConst) {
buffer.write("const ");
} else if (isFinal) {
buffer.write("final ");
}
if (declaredType is! VMTypeInstanceRef ||
(declaredType as VMTypeInstanceRef).name != "dynamic") {
buffer.write("$declaredType ");
} else if (!isConst && !isFinal) {
buffer.write("var ");
}
buffer.write(name);
return buffer.toString();
}
VMFieldRef._(Scope scope, Map json)
: _scope = scope,
_id = json["id"],
_fixedId = json["fixedId"] ?? false,
name = json["name"],
owner = _newLibraryOrClassRef(scope, json["owner"]),
declaredType = newVMTypeLikeInstanceRef(scope, json["declaredType"]),
isConst = json["const"],
isFinal = json["final"],
isStatic = json["static"];
/// Parses and returns either a [VMLibraryRef] or [VMClassRef].
static VMObjectRef _newLibraryOrClassRef(Scope scope, Map json) {
if (json == null) return null;
switch (json["type"]) {
case "@Library":
return newVMLibraryRef(scope, json);
case "@Class":
return newVMClassRef(scope, json);
default:
throw new StateError('Unexpected Object type "${json["type"]}".');
}
}
Future<VMField> load() async =>
new VMField._(_scope, await _scope.loadObject(_id));
bool operator ==(other) =>
other is VMFieldRef && (_fixedId ? _id == other._id : super == other);
int get hashCode => _fixedId ? _id.hashCode : super.hashCode;
String toString() => "$description = ...";
}
/// A field or variable.
class VMField extends VMFieldRef implements VMObject {
final VMClassRef klass;
final int size;
/// The value of this field.
///
/// This will be `null` unless this is a static field. The values of
/// non-static fields are available through [VMInstance.fields].
final VMInstanceRef value;
/// The lcoation of this field in the source code.
final VMSourceLocation location;
VMField._(Scope scope, Map json)
: klass = newVMClassRef(scope, json["class"]),
size = json["size"],
value = newVMInstanceRef(scope, json["staticValue"]),
location = newVMSourceLocation(scope, json["location"]),
super._(scope, json);
String toString() => "$description = ${value ?? '...'}";
}