progress
This commit is contained in:
parent
16e76d6b31
commit
484dbfc9d9
529 changed files with 113694 additions and 0 deletions
96
AspClassic.VBScript/Binders/VBScriptSetMemberBinder.cs
Normal file
96
AspClassic.VBScript/Binders/VBScriptSetMemberBinder.cs
Normal file
|
@ -0,0 +1,96 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
//using System.Text;
|
||||
using System.Reflection;
|
||||
using System.Dynamic;
|
||||
#if USE35
|
||||
using AspClassic.Scripting.Ast;
|
||||
using AspClassic.Scripting.ComInterop;
|
||||
#else
|
||||
using System.Linq.Expressions;
|
||||
using AspClassic.Scripting.ComInterop;
|
||||
#endif
|
||||
using Dlrsoft.VBScript.Runtime;
|
||||
|
||||
namespace Dlrsoft.VBScript.Binders
|
||||
{
|
||||
// VBScriptSetMemberBinder is used for general dotted expressions for setting
|
||||
// members.
|
||||
//
|
||||
public class VBScriptSetMemberBinder : SetMemberBinder
|
||||
{
|
||||
public VBScriptSetMemberBinder(string name)
|
||||
: base(name, true)
|
||||
{
|
||||
}
|
||||
|
||||
public override DynamicMetaObject FallbackSetMember(
|
||||
DynamicMetaObject targetMO, DynamicMetaObject value,
|
||||
DynamicMetaObject errorSuggestion)
|
||||
{
|
||||
#if !SILVERLIGHT
|
||||
// First try COM binding.
|
||||
DynamicMetaObject result;
|
||||
if (ComBinder.TryBindSetMember(this, targetMO, value, out result))
|
||||
{
|
||||
return result;
|
||||
}
|
||||
#endif
|
||||
// Defer if any object has no value so that we evaulate their
|
||||
// Expressions and nest a CallSite for the InvokeMember.
|
||||
if (!targetMO.HasValue) return Defer(targetMO);
|
||||
// Find our own binding.
|
||||
var flags = BindingFlags.IgnoreCase | BindingFlags.Static |
|
||||
BindingFlags.Instance | BindingFlags.Public;
|
||||
var members = targetMO.LimitType.GetMember(this.Name, flags);
|
||||
if (members.Length == 1)
|
||||
{
|
||||
MemberInfo mem = members[0];
|
||||
Expression val;
|
||||
// Should check for member domain type being Type and value being
|
||||
// TypeModel, similar to ConvertArguments, and building an
|
||||
// expression like GetRuntimeTypeMoFromModel.
|
||||
if (mem.MemberType == MemberTypes.Property)
|
||||
val = Expression.Convert(value.Expression,
|
||||
((PropertyInfo)mem).PropertyType);
|
||||
else if (mem.MemberType == MemberTypes.Field)
|
||||
val = Expression.Convert(value.Expression,
|
||||
((FieldInfo)mem).FieldType);
|
||||
else
|
||||
return (errorSuggestion ??
|
||||
RuntimeHelpers.CreateThrow(
|
||||
targetMO, null,
|
||||
BindingRestrictions.GetTypeRestriction(
|
||||
targetMO.Expression,
|
||||
targetMO.LimitType),
|
||||
typeof(InvalidOperationException),
|
||||
"Sympl only supports setting Properties and " +
|
||||
"fields at this time."));
|
||||
return new DynamicMetaObject(
|
||||
// Assign returns the stored value, so we're good for Sympl.
|
||||
RuntimeHelpers.EnsureObjectResult(
|
||||
Expression.Assign(
|
||||
Expression.MakeMemberAccess(
|
||||
Expression.Convert(targetMO.Expression,
|
||||
members[0].DeclaringType),
|
||||
members[0]),
|
||||
val)),
|
||||
// Don't need restriction test for name since this
|
||||
// rule is only used where binder is used, which is
|
||||
// only used in sites with this binder.Name.
|
||||
BindingRestrictions.GetTypeRestriction(targetMO.Expression,
|
||||
targetMO.LimitType));
|
||||
}
|
||||
else
|
||||
{
|
||||
return errorSuggestion ??
|
||||
RuntimeHelpers.CreateThrow(
|
||||
targetMO, null,
|
||||
BindingRestrictions.GetTypeRestriction(targetMO.Expression,
|
||||
targetMO.LimitType),
|
||||
typeof(MissingMemberException),
|
||||
"IDynObj member name conflict.");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue