Skip to content
This repository has been archived by the owner on Oct 23, 2019. It is now read-only.

Commit

Permalink
Merge commit '512c3c6f5dfb2dad9b4eede7761bdd0ef18ae18d'
Browse files Browse the repository at this point in the history
  • Loading branch information
jakubmisek committed Dec 23, 2015
2 parents 96648fc + 512c3c6 commit 1d64ede
Showing 1 changed file with 69 additions and 69 deletions.
138 changes: 69 additions & 69 deletions Source/Core/Binders/PhpGetMemberBinder.cs
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,21 @@ public override DynamicMetaObject Bind(DynamicMetaObject target, DynamicMetaObje
return FallbackInvokeMember(target, args);
}

static PhpReference notsetOperation(DObject self, string name, DTypeDesc caller, PhpReference refrnc)
{
bool getter_exists;
// the CT property has been unset -> try to invoke __get
PhpReference get_ref = self.InvokeGetterRef(name, caller, out getter_exists);
if (getter_exists) return get_ref ?? new PhpReference();

Debug.Assert(refrnc != null);

refrnc.IsAliased = true;
refrnc.IsSet = true;

return refrnc;
}

private DynamicMetaObject/*!*/ FallbackInvokeMember(DynamicMetaObject target/*!*/, DynamicMetaObject/*!*/[]/*!*/ args)
{
// determine run time values and additional restrictions:
Expand Down Expand Up @@ -193,21 +208,7 @@ public override DynamicMetaObject Bind(DynamicMetaObject target, DynamicMetaObje
//// reference.IsAliased = true;
//// reference.IsSet = true;
////}
Func<DObject, string, DTypeDesc, PhpReference, PhpReference> notsetOperation = (self, name, caller, refrnc) =>
{
bool getter_exists;
// the CT property has been unset -> try to invoke __get
PhpReference get_ref = self.InvokeGetterRef(name, caller, out getter_exists);
if (getter_exists) return get_ref ?? new PhpReference();
Debug.Assert(refrnc != null);
refrnc.IsAliased = true;
refrnc.IsSet = true;
return refrnc;
};


////return reference;

return new DynamicMetaObject(
Expand All @@ -216,7 +217,7 @@ public override DynamicMetaObject Bind(DynamicMetaObject target, DynamicMetaObje
new Expression[]{
isset,
Expression.Label(returnLabel,
Expression.Call(null, notsetOperation.Method, Expression.Convert(target.Expression, Types.DObject[0]), Expression.Constant(fieldName), Expression.Constant(classContext, Types.DTypeDesc[0]), reference))
Expression.Call(null, new Func<DObject, string, DTypeDesc, PhpReference, PhpReference>(notsetOperation).Method, Expression.Convert(target.Expression, Types.DObject[0]), Expression.Constant(fieldName), Expression.Constant(classContext, Types.DTypeDesc[0]), reference))
}),
restrictions);
}
Expand All @@ -235,16 +236,7 @@ public override DynamicMetaObject Bind(DynamicMetaObject target, DynamicMetaObje
////else return value;


Func<DObject, string, DTypeDesc, object> notsetOperation;
if (_issetSemantics) notsetOperation = (self, name, caller) =>
{
return PhpVariable.Dereference(self.GetRuntimeField(name, caller));
};
else notsetOperation = (self, name, caller) =>
{
bool handled;
return PhpVariable.Dereference(self.PropertyIssetHandler(name, caller, out handled));
};
var notsetOperation = _issetSemantics ? (Func<DObject, string, DTypeDesc, object>)GetMemberRuntimeFld : GetMemberIsSet;
var value =
Expression.Block(this._returnType,
new[] { reference },
Expand Down Expand Up @@ -334,34 +326,8 @@ public override DynamicMetaObject Bind(DynamicMetaObject target, DynamicMetaObje
case GetMemberResult.NotFound:
if (WantReference)
{
Func<DObject, string, DTypeDesc, PhpReference> op = (self, name, caller) =>
{
PhpReference reference;
bool getter_exists;
// search in RT fields
if (self.RuntimeFields != null && self.RuntimeFields.ContainsKey(name))
{
var namekey = new IntStringKey(name);
return self.RuntimeFields.table._ensure_item_ref(ref namekey, self.RuntimeFields);
}
// property is not present -> try to invoke __get
reference = self.InvokeGetterRef(name, caller, out getter_exists);
if (getter_exists) return (reference == null) ? new PhpReference() : reference;
// (no notice/warning/error thrown by PHP)
// add the field
reference = new PhpReference();
if (self.RuntimeFields == null) self.RuntimeFields = new PhpArray();
self.RuntimeFields[name] = reference;
return reference;
};

return new DynamicMetaObject(
Expression.Call(null, op.Method, Expression.Convert(target.Expression, Types.DObject[0]), Expression.Constant(fieldName), Expression.Constant(classContext, Types.DTypeDesc[0])),
Expression.Call(null, new Func<DObject, string, DTypeDesc, PhpReference>(GetRefMemberNotFound).Method, Expression.Convert(target.Expression, Types.DObject[0]), Expression.Constant(fieldName), Expression.Constant(classContext, Types.DTypeDesc[0])),
restrictions);
}
else
Expand All @@ -383,22 +349,9 @@ public override DynamicMetaObject Bind(DynamicMetaObject target, DynamicMetaObje

if (_issetSemantics)
{
Func<DObject, string, DTypeDesc, object> notsetOperation = (self, name, caller) =>
{
if (self.RuntimeFields != null)
{
object value;
if (self.RuntimeFields.TryGetValue(name, out value))
return value;
}
bool handled;
return self.PropertyIssetHandler(name, caller, out handled);
};

return new DynamicMetaObject(
Expression.Call(Methods.PhpVariable.Dereference,
Expression.Call(null, notsetOperation.Method, Expression.Convert(target.Expression, Types.DObject[0]), Expression.Constant(fieldName), Expression.Constant(classContext, Types.DTypeDesc[0]))),
Expression.Call(null, new Func<DObject, string, DTypeDesc, object>(GetMemberNotFoundIsSet).Method, Expression.Convert(target.Expression, Types.DObject[0]), Expression.Constant(fieldName), Expression.Constant(classContext, Types.DTypeDesc[0]))),
restrictions);
}
else
Expand All @@ -411,8 +364,6 @@ public override DynamicMetaObject Bind(DynamicMetaObject target, DynamicMetaObje
Methods.DObject_GetRuntimeField, Expression.Constant(fieldName), Expression.Constant(classContext, Types.DTypeDesc[0]))),
restrictions);
};


}
case GetMemberResult.BadVisibility:
{
Expand Down Expand Up @@ -476,5 +427,54 @@ public override DynamicMetaObject Bind(DynamicMetaObject target, DynamicMetaObje
BindingRestrictions.GetInstanceRestriction(target.Expression, null) :
BindingRestrictions.GetTypeRestriction(target.Expression, target.LimitType));
}

static object GetMemberRuntimeFld(DObject self, string name, DTypeDesc caller)
{
return PhpVariable.Dereference(self.GetRuntimeField(name, caller));
}

static object GetMemberIsSet(DObject self, string name, DTypeDesc caller)
{
return PhpVariable.Dereference(self.GetRuntimeField(name, caller));
}

static PhpReference GetRefMemberNotFound(DObject self, string name, DTypeDesc caller)
{
PhpReference reference;
bool getter_exists;

// search in RT fields
if (self.RuntimeFields != null && self.RuntimeFields.ContainsKey(name))
{
var namekey = new IntStringKey(name);
return self.RuntimeFields.table._ensure_item_ref(ref namekey, self.RuntimeFields);
}

// property is not present -> try to invoke __get
reference = self.InvokeGetterRef(name, caller, out getter_exists);
if (getter_exists) return (reference == null) ? new PhpReference() : reference;

// (no notice/warning/error thrown by PHP)

// add the field
reference = new PhpReference();
if (self.RuntimeFields == null) self.RuntimeFields = new PhpArray();
self.RuntimeFields[name] = reference;

return reference;
}

static object GetMemberNotFoundIsSet(DObject self, string name, DTypeDesc caller)
{
if (self.RuntimeFields != null)
{
object value;
if (self.RuntimeFields.TryGetValue(name, out value))
return value;
}

bool handled;
return self.PropertyIssetHandler(name, caller, out handled);
}
}
}

0 comments on commit 1d64ede

Please sign in to comment.