| Index: frog/frogsh
|
| diff --git a/frog/frogsh b/frog/frogsh
|
| index d520b95b5e4dfb92e96bfce9d5ec708554830f93..3903ba90a455f46ed0af800051ae6b5964e07fc8 100755
|
| --- a/frog/frogsh
|
| +++ b/frog/frogsh
|
| @@ -1092,6 +1092,9 @@ ImmutableMap.prototype.containsKey = function(key) {
|
| ImmutableMap.prototype.$setindex = function(key, value) {
|
| $throw(const$14/*const IllegalAccessException()*/);
|
| }
|
| +ImmutableMap.prototype.putIfAbsent = function(key, ifAbsent) {
|
| + $throw(const$14/*const IllegalAccessException()*/);
|
| +}
|
| ImmutableMap.prototype.forEach$1 = ImmutableMap.prototype.forEach;
|
| ImmutableMap.prototype.getKeys$0 = function() {
|
| return this.getKeys();
|
| @@ -1291,6 +1294,13 @@ HashMapImplementation.prototype.$index = function(key) {
|
| if (index < 0) return null;
|
| return this._values.$index(index);
|
| }
|
| +HashMapImplementation.prototype.putIfAbsent = function(key, ifAbsent) {
|
| + var index = this._probeForLookup(key);
|
| + if (index >= 0) return this._values.$index(index);
|
| + var value = ifAbsent();
|
| + this.$setindex(key, value);
|
| + return value;
|
| +}
|
| HashMapImplementation.prototype.remove = function(key) {
|
| var index = this._probeForLookup(key);
|
| if (index >= 0) {
|
| @@ -1729,6 +1739,14 @@ LinkedHashMapImplementation.prototype.$index = function(key) {
|
| if (entry == null) return null;
|
| return entry.get$element().get$value();
|
| }
|
| +LinkedHashMapImplementation.prototype.putIfAbsent = function(key, ifAbsent) {
|
| + var value = this.$index(key);
|
| + if ((this.$index(key) == null) && !(this.containsKey(key))) {
|
| + value = ifAbsent();
|
| + this.$setindex(key, value);
|
| + }
|
| + return value;
|
| +}
|
| LinkedHashMapImplementation.prototype.getKeys = function() {
|
| var list = new ListFactory(this.get$length());
|
| var index = 0;
|
| @@ -14197,12 +14215,39 @@ MethodMember.prototype.invoke = function(context, node, target, args, isDynamic)
|
| return new Value(this.get$inferredResult(), code, node.span, true);
|
| }
|
| MethodMember.prototype._invokeConstructor = function(context, node, target, args, argsString) {
|
| + var $0;
|
| this.declaringType.markUsed();
|
| if (!$notnull_bool(target.isType)) {
|
| var code = (this.get$constructorName() != '') ? ('' + this.declaringType.get$jsname() + '.' + this.get$constructorName() + '\$ctor.call(' + argsString + ')') : ('' + this.declaringType.get$jsname() + '.call(' + argsString + ')');
|
| return new Value(target.type, code, node.span, true);
|
| }
|
| else {
|
| + if ($notnull_bool(this.declaringType.get$isAbstract())) {
|
| + $globals.world.warning(('Cannot instantiate abstract class ' + this.declaringType.name), node.span);
|
| + var members = groupBy((($0 = this.declaringType.get$inheritedMembers().getValues().filter$1((function (m) {
|
| + return m.get$isAbstract();
|
| + })
|
| + )) && $0.is$Iterable()), (function (m) {
|
| + return m.get$declaringType();
|
| + })
|
| + );
|
| + var msg = new StringBufferImpl(('Type ' + this.declaringType.name + ' is abstract ') + 'because it does not implement the following members');
|
| + var types = members.getKeys$0();
|
| + types.sort$1((function (x, y) {
|
| + return x.get$name().compareTo$1(y.get$name());
|
| + })
|
| + );
|
| + for (var $i = types.iterator$0(); $i.hasNext$0(); ) {
|
| + var type = $i.next$0();
|
| + if ($notnull_bool($ne(type, types.$index(0)))) msg.add$1(';');
|
| + msg.add$1((' from type ' + type.get$name() + ': '));
|
| + msg.add$1(Strings.join(map((($0 = members.$index(type)) && $0.is$Iterable()), (function (m) {
|
| + return m.get$name();
|
| + })
|
| + ), ', '));
|
| + }
|
| + $globals.world.warning(msg.toString$0(), this.declaringType.get$span());
|
| + }
|
| var code = (this.get$constructorName() != '') ? ('new ' + this.declaringType.get$jsname() + '.' + this.get$constructorName() + '\$ctor(' + argsString + ')') : ('new ' + this.declaringType.get$jsname() + '(' + argsString + ')');
|
| if ($notnull_bool(this.isConst) && (node instanceof lang_NewExpression) && $notnull_bool(node.get$dynamic().get$isConst())) {
|
| return this._invokeConstConstructor(node, $assert_String(code), target, args);
|
| @@ -19455,6 +19500,45 @@ lang_Type.prototype.getAllMembers = function() {
|
| lang_Type.prototype.hashCode = function() {
|
| return this.name.hashCode();
|
| }
|
| +lang_Type.prototype.get$isAbstract = function() {
|
| + if (this._isAbstract == null) {
|
| + if ($notnull_bool(this.get$isClass())) {
|
| + this._isAbstract = $assert_bool(this.get$inheritedMembers().getValues().some$1((function (m) {
|
| + return m.get$isAbstract();
|
| + })
|
| + ));
|
| + }
|
| + else {
|
| + this._isAbstract = true;
|
| + }
|
| + }
|
| + return this._isAbstract;
|
| +}
|
| +lang_Type.prototype.get$inheritedMembers = function() {
|
| + var $0;
|
| + if (this._inheritedMembers == null) {
|
| + this._inheritedMembers = (($0 = this._getInheritedMembers($map([]))) && $0.is$Map$String$Member());
|
| + }
|
| + return this._inheritedMembers;
|
| +}
|
| +lang_Type.prototype._getInheritedMembers = function(flattened) {
|
| + if (this.get$interfaces() != null) {
|
| + var $list = this.get$interfaces();
|
| + for (var $i = 0;$i < $list.length; $i++) {
|
| + var i = $list.$index($i);
|
| + i._getInheritedMembers(flattened);
|
| + }
|
| + }
|
| + if (this.get$parent() != null) {
|
| + this.get$parent()._getInheritedMembers(flattened);
|
| + }
|
| + var $list = this.getAllMembers().getValues();
|
| + for (var $i = this.getAllMembers().getValues().iterator$0(); $i.hasNext$0(); ) {
|
| + var m = $i.next$0();
|
| + flattened.$setindex(m.get$name(), m);
|
| + }
|
| + return flattened;
|
| +}
|
| lang_Type.prototype._checkOverride = function(member) {
|
| var parentMember = this._getMemberInParents(member.name);
|
| if ($notnull_bool($ne(parentMember, null))) {
|
| @@ -20076,7 +20160,7 @@ DefinedType.prototype.set$isUsed = function(value) { return this.isUsed = value;
|
| DefinedType.prototype.get$isNativeType = function() { return this.isNativeType; };
|
| DefinedType.prototype.set$isNativeType = function(value) { return this.isNativeType = value; };
|
| DefinedType.prototype.setDefinition = function(def) {
|
| - $assert(this.definition == null, "definition == null", "type.dart", 703, 12);
|
| + $assert(this.definition == null, "definition == null", "type.dart", 747, 12);
|
| this.definition = def;
|
| if ((this.definition instanceof TypeDefinition) && this.definition.get$nativeType() != null) {
|
| this.isNativeType = true;
|
| @@ -20186,7 +20270,7 @@ DefinedType.prototype._resolveInterfaces = function(types) {
|
| return (interfaces && interfaces.is$List$Type());
|
| }
|
| DefinedType.prototype.addDirectSubtype = function(type) {
|
| - $assert(this._subtypes == null, "_subtypes == null", "type.dart", 819, 12);
|
| + $assert(this._subtypes == null, "_subtypes == null", "type.dart", 863, 12);
|
| this.directSubtypes.add(type);
|
| }
|
| DefinedType.prototype.get$subtypes = function() {
|
| @@ -20564,7 +20648,7 @@ DefinedType.prototype.resolveTypeParams = function(inType) {
|
| return this;
|
| }
|
| DefinedType.prototype.getOrMakeConcreteType = function(typeArgs) {
|
| - $assert(this.get$isGeneric(), "isGeneric", "type.dart", 1248, 12);
|
| + $assert(this.get$isGeneric(), "isGeneric", "type.dart", 1292, 12);
|
| var names = [this.name];
|
| var typeMap = $map([]);
|
| for (var i = 0;
|
| @@ -20582,7 +20666,7 @@ DefinedType.prototype.getOrMakeConcreteType = function(typeArgs) {
|
| return (ret && ret.is$lang_Type());
|
| }
|
| DefinedType.prototype.getCallStub = function(args) {
|
| - $assert(this.get$isFunction(), "isFunction", "type.dart", 1268, 12);
|
| + $assert(this.get$isFunction(), "isFunction", "type.dart", 1312, 12);
|
| var name = _getCallStubName('call', args);
|
| if (this.varStubs == null) this.varStubs = $map([]);
|
| var stub = this.varStubs.$index(name);
|
| @@ -21936,7 +22020,7 @@ VarMethodSet.prototype.invoke$4 = function($0, $1, $2, $3) {
|
| };
|
| // ********** Code for top level **************
|
| function map(source, mapper) {
|
| - var result = new ListFactory();
|
| + var result = [];
|
| if (!!(source && source.is$List)) {
|
| var list = (source && source.is$List());
|
| result.length = list.length;
|
| @@ -21964,6 +22048,18 @@ function reduce(source, callback, initialValue) {
|
| }
|
| return current;
|
| }
|
| +function groupBy(left, keyFn) {
|
| + var result = $map([]);
|
| + var iter = left.iterator();
|
| + while ($notnull_bool(iter.hasNext$0())) {
|
| + var i = iter.next$0();
|
| + result.putIfAbsent(keyFn(i), (function () {
|
| + return [];
|
| + })
|
| + ).add$1(i);
|
| + }
|
| + return result;
|
| +}
|
| function orderValuesByKeys(map) {
|
| var $0;
|
| var keys = (($0 = map.getKeys()) && $0.is$List());
|
|
|