private static CSharpFile FileScan(string className, bool required) { if (FileScanCache.ContainsKey(className)) { return(FileScanCache[className]); } int indexer = className.IndexOf('<'); if (indexer != -1) { className = className.Substring(0, indexer); } string fileSpec = string.Format("\\{0}.cs", className); string alternativeFileSpec = string.Format("\\{0}.cpp", className); List <string> files = _fileList.Where(x => x.EndsWith(fileSpec) || x.EndsWith(alternativeFileSpec)).ToList(); files = ExcludeFiles(files); if (files.Count > 1) { string error = string.Format("Ambiguous file spec {0}", fileSpec); throw new Exception(error); } if (files.Count == 0 && required) { string error = string.Format("Cannot find file spec for {0}", fileSpec); throw new Exception(error); } string file = files.SingleOrDefault(); if (file == null) { return(null); } var csFile = new CSharpFile(className); csFile.ParseFile(new FileInfo(file)); FileScanCache[className] = csFile; return(csFile); }
private static bool RenderPropertyInjections(StringWriter rw, CSharpFile fileDefinition) { var hasProperties = false; foreach (var propertyInjection in fileDefinition.PropertyInjections) { string interfaceRequired = propertyInjection.Key; string concreteFunction = GetConcreteYieldingFunction(interfaceRequired); rw.WriteLine("x.{0} = {1};", propertyInjection.Value, concreteFunction); hasProperties = true; } foreach (string baseType in fileDefinition.BaseTypes) { if (_injectionSpecification.Exclude != null) { bool isExcludedBaseType = _injectionSpecification.Exclude.Any(b => Regex.IsMatch(baseType, b.Value)); if (isExcludedBaseType) { continue; } } // TODO - really ropey interface detection... if (baseType.StartsWith("I") && char.IsUpper(baseType.ElementAt(1))) { continue; } CSharpFile x = FileScan(baseType, true); hasProperties |= RenderPropertyInjections(rw, x); } return(hasProperties); }
private static void RenderConcreteBuilderGetter(StringWriter rw, InjectionSpecificationInjection injection, EmittedKernelSpec spec) { if (!string.IsNullOrEmpty(injection.Provider)) { throw new ParseException("Injection concrete '{0}' alse has provider '{1}' defined", injection.Concrete, injection.Provider); } string concreteToBuild = injection.Concrete; CSharpFile fileDefinition = injection.NoScan ? new CSharpFile(concreteToBuild) : FileScan(concreteToBuild, true); if (injection.Singleton) { rw.WriteLine("static {0}() {{", injection.ConcreteClassName); rw.WriteLine("{0} = new Lazy<{1}>(() => {{", spec.PrivateFieldName, spec.PrivateFieldType); } else { rw.WriteLine("{0} static {1} Get() {{", _renderAccessModifier, spec.ReturnType); } // There is no StackTrace on Metro :-( if (!_inputTokens.Contains("NETFX_CORE")) { if (!spec.IsDebug) { rw.WriteLine("#if DEBUG"); } rw.WriteLine("var stack = new StackTrace().GetFrames();"); rw.WriteLine("var methodName = stack.First().GetMethod().DeclaringType.Name;"); rw.WriteLine("if (stack.Count(y => y.GetMethod().DeclaringType.Name == methodName) > 2) { throw new Exception(\"Infinite loop detected\"); }"); if (!spec.IsDebug) { rw.WriteLine("#endif"); } } if (_benchmarking) { if (!spec.IsDebug) { rw.WriteLine("#if DEBUG"); } rw.WriteLine("Debug.WriteLine(\"Thread(\" + System.Threading.Thread.CurrentThread.ManagedThreadId + \") : Kernel TypeConstruct: {0}\");", injection.ConcreteClassName); rw.WriteLine("var stopWatch = System.Diagnostics.Stopwatch.StartNew();"); if (!spec.IsDebug) { rw.WriteLine("#endif"); } } rw.WriteLine("var x = new {0}(", concreteToBuild); if (injection.ConstructorArgument != null && injection.ConstructorArgument.Length > 0) { InjectionSpecificationInjectionConstructorArgument[] cArgs = injection.ConstructorArgument; for (int i = 0; i < cArgs.Length; i++) { if (i != 0) { rw.Write(','); } rw.WriteLine(injection.ConstructorArgument[i].Value); } } else { IList <string> cArgs = fileDefinition.ConstructorArgs ?? new List <string>(); for (int i = 0; i < cArgs.Count; i++) { if (i != 0) { rw.Write(','); } string interfaceRequired = cArgs[i]; string concreteFunction = GetConcreteYieldingFunction(interfaceRequired); rw.WriteLine(concreteFunction); } } rw.WriteLine(");"); if (_benchmarking) { if (!spec.IsDebug) { rw.WriteLine("#if DEBUG"); } rw.WriteLine("stopWatch.Stop();"); rw.WriteLine("Debug.WriteLine(\"Thread(\" + System.Threading.Thread.CurrentThread.ManagedThreadId + \") : Kernel TypeConstruct: {0}, MillisecondsElapsed: \" + stopWatch.ElapsedMilliseconds);", injection.ConcreteClassName); if (!spec.IsDebug) { rw.WriteLine("#endif"); } } if (!injection.NoScan) { if (_benchmarking) { if (!spec.IsDebug) { rw.WriteLine("#if DEBUG"); } rw.WriteLine("stopWatch = System.Diagnostics.Stopwatch.StartNew();"); if (!spec.IsDebug) { rw.WriteLine("#endif"); } } var hasProperties = RenderPropertyInjections(rw, fileDefinition); if (_benchmarking) { if (!spec.IsDebug) { rw.WriteLine("#if DEBUG"); } rw.WriteLine("stopWatch.Stop();"); if (hasProperties) { rw.WriteLine("Debug.WriteLine(\"Thread(\" + System.Threading.Thread.CurrentThread.ManagedThreadId + \") : Kernel TypePropertiesSet: {0}, MillisecondsElapsed: \" + stopWatch.ElapsedMilliseconds);", injection.ConcreteClassName); } if (!spec.IsDebug) { rw.WriteLine("#endif"); } } } rw.WriteLine("return x;"); if (injection.Singleton) { rw.WriteLine("});"); rw.WriteLine("}"); rw.WriteLine("{0} static {1} Get() {{ return {2}.Value; }}", _renderAccessModifier, spec.ReturnType, spec.PrivateFieldName); rw.WriteLine("{0} static Lazy<{1}> GetLazy() {{ return {2}; }}", _renderAccessModifier, spec.ReturnType, spec.PrivateFieldName); } else { rw.WriteLine("}"); rw.WriteLine("{0} static Lazy<{1}> GetLazy() {{ return new Lazy<{1}>(Get); }}", _renderAccessModifier, spec.ReturnType, spec.PrivateFieldName); } }
private static void RenderPropertyInjections(StringWriter rw, CSharpFile fileDefinition) { foreach (var propertyInjection in fileDefinition.PropertyInjections) { string interfaceRequired = propertyInjection.Key; string concreteFunction = GetConcreteYieldingFunction(interfaceRequired); rw.WriteLine("x.{0} = {1};", propertyInjection.Value, concreteFunction); } foreach (string baseType in fileDefinition.BaseTypes) { if (_injectionSpecification.Exclude != null) { bool isExcludedBaseType = _injectionSpecification.Exclude.Any(b => Regex.IsMatch(baseType, b.Value)); if (isExcludedBaseType) { continue; } } // TODO - really ropey interface detection... if (baseType.StartsWith("I") && char.IsUpper(baseType.ElementAt(1))) { continue; } CSharpFile x = FileScan(baseType, true); RenderPropertyInjections(rw, x); } }
private static CSharpFile FileScan(string className, bool required) { if (FileScanCache.ContainsKey(className)) { return FileScanCache[className]; } int indexer = className.IndexOf('<'); if (indexer != -1) { className = className.Substring(0, indexer); } string fileSpec = string.Format("\\{0}.cs", className); string alternativeFileSpec = string.Format("\\{0}.cpp", className); List<string> files = _fileList.Where(x => x.EndsWith(fileSpec) || x.EndsWith(alternativeFileSpec)).ToList(); files = ExcludeFiles(files); if (files.Count > 1) { string error = string.Format("Ambiguous file spec {0}", fileSpec); throw new Exception(error); } if (files.Count == 0 && required) { string error = string.Format("Cannot find file spec for {0}", fileSpec); throw new Exception(error); } string file = files.SingleOrDefault(); if (file == null) { return null; } var csFile = new CSharpFile(className); csFile.ParseFile(new FileInfo(file)); FileScanCache[className] = csFile; return csFile; }