/// <summary> /// Given this membrane's outbound list, what membranes are inbound permeabe to the ST as well? /// </summary> public List <IMembrane> PermeateTo(ISemanticType st) { List <IMembrane> ret = new List <IMembrane>(); Type sttype = st.GetType(); if (outboundPermeableTo.Contains(sttype)) { // Can we traverse to the parent? if ((parent != null) && (parent.inboundPermeableTo.Contains(sttype))) { ret.Add(parent); } // Can we traverse to children? foreach (Membrane child in childMembranes) { if (child.inboundPermeableTo.Contains(sttype)) { ret.Add(child); } } } return(ret); }
public App(LogicalForm f, LogicalForm x) : base(null) { ISemanticType fType = f.GetSemanticType(); ISemanticType xType = x.GetSemanticType(); if (fType.GetType() != typeof(Arrow)) { System.Console.WriteLine( "App failed: function argument not function type"); return; } Arrow aType = (Arrow)fType; if (!aType.GetInputType().Equals(xType)) { // error System.Console.WriteLine("App failed: type mismatch"); // throw new InvalidTypeException(); return; } this.type = aType.GetOutputType(); this.isFormula = this.type.GetType() == typeof(T); this.freeVariables = f.MergeVariables(x); this.f = f; this.x = x; }
public void Process(ISemanticProcessor semProc, IMembrane membrane, ISemanticType t) { if ( (!(t is ST_Log)) && (!(t is ST_Exception)) ) { Console.WriteLine("Publishing type: " + t.GetType().Name); } }
public void Process(ISemanticProcessor semProc, IMembrane membrane, ISemanticType t) { if ((!(t is ST_Log)) && (!(t is ST_Exception))) { Console.WriteLine("Publishing type: " + t.GetType().Name); } }
/// <summary> /// Any public properties that are of ISemanticType type and not null are also emitted into the membrane. /// </summary> protected void ProcessInnerTypes(IMembrane membrane, IMembrane caller, ISemanticType obj, bool processOnCallerThread) { var properties = obj.GetType().GetProperties(BindingFlags.Instance | BindingFlags.Public).Where(pi => pi.PropertyType.GetInterfaces().Contains(typeof(ISemanticType))); properties.ForEach(pi => { ISemanticType prop = (ISemanticType)pi.GetValue(obj); prop.IfNotNull((p) => ProcessInstance(membrane, caller, p, processOnCallerThread)); }); }
public void Process(ISemanticProcessor proc, IMembrane membrane, ISemanticType type) { // Don't log our log message, otherwise we get an infinite loop! if (!(type is ST_Log)) { // One way, with instances: // proc.ProcessInstance(proc.Logger, new ST_Log() { Message = type.GetType().ToString() }); // Another way, strictly with types: proc.ProcessInstance<LoggerMembrane, ST_Log>(log => log.Message = type.GetType().ToString()); } }
public void Process(ISemanticProcessor proc, IMembrane membrane, ISemanticType type) { // Don't log our log message, otherwise we get an infinite loop! if (!(type is ST_Log)) { // One way, with instances: // proc.ProcessInstance(proc.Logger, new ST_Log() { Message = type.GetType().ToString() }); // Another way, strictly with types: proc.ProcessInstance <LoggerMembrane, ST_Log>(log => log.Message = type.GetType().ToString()); } }
protected void PopulateType(ISemanticType packet, Dictionary <string, string> data) { foreach (string key in data.Keys) { PropertyInfo pi = packet.GetType().GetProperty(key, BindingFlags.Public | BindingFlags.Instance | BindingFlags.IgnoreCase); if (pi != null) { object valOfType = Convert.ChangeType(data[key], pi.PropertyType); pi.SetValue(packet, valOfType); } } }
protected void PopulateType(ISemanticType packet, NameValueCollection nvc) { foreach (string key in nvc.AllKeys) { PropertyInfo pi = packet.GetType().GetProperty(key, BindingFlags.Public | BindingFlags.Instance | BindingFlags.IgnoreCase); if (pi != null) { object valOfType = Convert.ChangeType(Uri.UnescapeDataString(nvc[key].Replace('+', ' ')), pi.PropertyType); pi.SetValue(packet, valOfType); } } }
// Super compatible private HashSet <int> GetDomain(ISemanticType t) { Model currentModel = super; if (t.GetType() == typeof(FType)) { FType fType = (FType)t; LogicalForm formula = fType.GetFormula(); int varID = formula.GetFreeVariables().Single <Variable>().GetID(); ISemanticType baseType = fType.GetBaseType(); // populating the set with all semantic values // (including those in super models) // possible error: basetype is undefined in M Dictionary <int, ISemanticValue> .KeyCollection baseSet = model[baseType].Keys; while (currentModel != null) { // possible error: basetype is undefined in M baseSet.Union <int>(currentModel.model[baseType].Keys); } HashSet <int> finalSet = new HashSet <int>(); foreach (int i in baseSet) { if (Satisfies(formula.Bind(varID, new Constant(baseType, i)))) { finalSet.Add(i); } } return(finalSet); } HashSet <int> theSet = new HashSet <int>(); foreach (int i in model[t].Keys) { theSet.Add(i); } while (currentModel != null) { // possible error: t is undefined in M theSet.UnionWith(currentModel.model[t].Keys); } return(theSet); }
/// <summary> /// Any public properties that are of ISemanticType type and not null are also emitted into the membrane. /// </summary> protected void ProcessInnerTypes(IMembrane membrane, IMembrane caller, ISemanticType obj, bool processOnCallerThread, IMembrane fromMembrane, IReceptor fromReceptor) { // TODO: Setup like we do for main ProcessInstance above so exceptions are caught and we get a ProcStates return. // ProcStates ps = ProcStates.NotProcessed; var properties = obj.GetType().GetProperties(BindingFlags.Instance | BindingFlags.Public).Where(pi => pi.PropertyType.GetInterfaces().Contains(typeof(ISemanticType))); properties.ForEach(pi => { ISemanticType prop = (ISemanticType)pi.GetValue(obj); if (prop != null) { // TODO: Setup like we do for main ProcessInstance above so exceptions are caught and we get a ProcStates return. ProcessInstanceWithInvoke(membrane, caller, prop, processOnCallerThread); } }); }
protected void PopulateType(ISemanticType packet, Dictionary <string, string> data) { foreach (string key in data.Keys) { PropertyInfo pi = packet.GetType().GetProperty(key, BindingFlags.Public | BindingFlags.Instance | BindingFlags.IgnoreCase); if (pi != null) { object valOfType = null; Type ptype = pi.PropertyType; if (ptype.IsGenericType) { // We assume it's a nullable type ptype = ptype.GenericTypeArguments[0]; } valOfType = Convert.ChangeType(Uri.UnescapeDataString(data[key].Replace('+', ' ')), ptype); pi.SetValue(packet, valOfType); } } }
/// <summary> /// Process an instance where we only know that it implements ISemanticType as opposed the the concrete type in the generic method above. /// We cannot use "dynamic" in this case, therefore we have to use Method.Invoke. /// </summary> protected void ProcessInstance(IMembrane membrane, IMembrane caller, ISemanticType obj, bool processOnCallerThread = false) { // We get the source object type. Type tsource = obj.GetType(); // Stateless receptors: List <Type> receptors = GetReceptors(membrane, tsource); Log(membrane, obj); foreach (Type ttarget in receptors) { // We can use dynamic here because we have a <T> generic to resolve the call parameter. // If we instead only have the interface ISemanticType, dynamic does not downcast to the concrete type -- // therefore it can't locate the call point because it implements the concrete type. IReceptor target = (IReceptor)Activator.CreateInstance(ttarget); ReceptorInitializer receptorInitializer; if (receptorInitializers.TryGetValue(new MembraneReceptor() { Membrane = membrane, ReceptorType = ttarget }, out receptorInitializer)) { receptorInitializer.Initializer(target); } // Call immediately? MethodInfo method = GetProcessMethod(target, tsource); if (processOnCallerThread) { method.Invoke(target, new object[] { this, membrane, obj }); } else { // Pick a thread that has the least work to do. threadPool.MinBy(tp => tp.Count).Enqueue(new MethodInvokeCall() { Method = method, SemanticInstance = obj, Receptor = target, Parameters = new object[] { this, membrane, obj } }); } } // Also check stateful receptors List <IReceptor> sreceptors = GetStatefulReceptors(membrane, tsource); foreach (IReceptor receptor in sreceptors) { MethodInfo method = GetProcessMethod(receptor, tsource); // Call immediately? if (processOnCallerThread) { method.Invoke(receptor, new object[] { this, membrane, obj }); } else { threadPool.MinBy(tp => tp.Count).Enqueue(new MethodInvokeCall() { Method = method, SemanticInstance = obj, Receptor = receptor, Parameters = new object[] { this, membrane, obj }, AutoDispose = false }); } } ProcessInnerTypes(membrane, caller, obj, processOnCallerThread); PermeateOut(membrane, caller, obj, processOnCallerThread); }
/// <summary> /// Get the current qualified state of all receptors that are to be triggered. /// </summary> protected Dictionary <SemanticQualifier, bool> CaptureQualifierState(List <IReceptor> receptors, ISemanticType obj) { Dictionary <SemanticQualifier, bool> qstate = new Dictionary <SemanticQualifier, bool>(); qualifiers.ForEach(q => qstate[q] = false); foreach (IReceptor receptor in receptors) { var checkReceptors = qualifiers.Where(q => q.Receptor == receptor && q.SemanticType == obj.GetType()); checkReceptors.ForEach(q => qstate[q] = q.Qualifier((ISemanticQualifier)obj)); } return(qstate); }
/// <summary> /// Return true if the receptor-semantic type pair does not have any qualifiers, /// or if it does, that at least one qualifier returns true. /// </summary> protected bool IsQualified(Dictionary <SemanticQualifier, bool> qstate, IReceptor receptor, ISemanticType obj) { bool ret = true; // Only stateful receptors can have qualifiers, since the qualifier tests against a receptor state. var checkReceptors = qualifiers.Where(q => q.Receptor == receptor && q.SemanticType == obj.GetType()); if (checkReceptors.Count() > 0) { ret = checkReceptors.Any(q => qstate[q]); } return(ret); }
protected static bool IsFormulaType(ISemanticType t) { return(t.GetType() == typeof(T) || t.GetType() == typeof(W) || t.GetType() == typeof(G)); }
// TODO: We're not providing an option to set the thread timeout here! /// <summary> /// Process an instance where we only know that it implements ISemanticType as opposed the the concrete type in the generic method above. /// We cannot use "dynamic" in this case, therefore we have to use Method.Invoke. /// </summary> protected void ProcessInstanceWithInvoke(IMembrane membrane, IMembrane caller, ISemanticType obj, bool processOnCallerThread = false, IMembrane fromMembrane = null, IReceptor fromReceptor = null) { // TODO: Setup like we do for main ProcessInstance above so exceptions are caught and we get a ProcStates return. // ProcStates ps = ProcStates.NotProcessed; // We get the source object type. Type tsource = obj.GetType(); // Stateless receptors: List <Type> receptors = GetReceptors(membrane, tsource); Log(membrane, obj); foreach (Type ttarget in receptors) { // We can use dynamic here because we have a <T> generic to resolve the call parameter. // If we instead only have the interface ISemanticType, dynamic does not downcast to the concrete type -- // therefore it can't locate the call point because it implements the concrete type. IReceptor target = (IReceptor)Activator.CreateInstance(ttarget); ReceptorInitializer receptorInitializer; if (receptorInitializers.TryGetValue(new MembraneReceptor() { Membrane = membrane, ReceptorType = ttarget }, out receptorInitializer)) { receptorInitializer.Initializer(target); } MethodInfo method = GetProcessMethod(target, tsource); // Call immediately? if (processOnCallerThread || ForceSingleThreaded) { // TODO: Setup like we do for main ProcessInstance above so exceptions are caught and we get a ProcStates return. // dynamic dtarget = target; // ps |= Call(new DynamicCall() { SemanticInstance = obj, Receptor = target, Proc = () => dtarget.Process(this, membrane, obj), AutoDispose = false }); Processing.Fire(this, new ProcessEventArgs(fromMembrane, fromReceptor, membrane, target, obj)); method.Invoke(target, new object[] { this, membrane, obj }); } else { #if USE_THREAD_POOL QueueInvokeCall(obj, method, target, fromMembrane, fromReceptor, membrane, 0, false); #else Task.Run(() => { Processing.Fire(this, new ProcessEventArgs(fromMembrane, fromReceptor, membrane, target, obj)); method.Invoke(target, new object[] { this, membrane, obj }); // target.Process(this, membrane, obj); }); #endif } } // Also check stateful receptors List <IReceptor> sreceptors = GetStatefulReceptors(membrane, tsource); Dictionary <SemanticQualifier, bool> qstate = CaptureQualifierState(sreceptors, obj); foreach (IReceptor receptor in sreceptors) { // Only stateful receptors can have qualifiers, since the qualifier tests against a receptor state. if (IsQualified(qstate, receptor, obj)) { MethodInfo method = GetProcessMethod(receptor, tsource); // Call immediately? if (processOnCallerThread || ForceSingleThreaded) { Processing.Fire(this, new ProcessEventArgs(fromMembrane, fromReceptor, membrane, receptor, obj)); method.Invoke(receptor, new object[] { this, membrane, obj }); } else { #if USE_THREAD_POOL QueueInvokeCall(obj, method, receptor, fromMembrane, fromReceptor, membrane, 0, false); #else Task.Run(() => { Processing.Fire(this, new ProcessEventArgs(fromMembrane, fromReceptor, membrane, receptor, obj)); method.Invoke(receptor, new object[] { this, membrane, obj }); }); #endif } } } ProcessInnerTypes(membrane, caller, obj, processOnCallerThread, fromMembrane, fromReceptor); PermeateOut(membrane, caller, obj, processOnCallerThread, fromMembrane, fromReceptor); }