//generate the code from the parsed BrowserDefinitionTree //compile it, and install it in the gac private void GenerateAssembly() { Debug.Assert(_browserTree != null); BrowserDefinition root = (BrowserDefinition)_browserTree["Default"]; BrowserDefinition defaultRoot = (BrowserDefinition)_defaultTree["Default"]; ArrayList customTreeRoots = new ArrayList(); for (int i = 0; i < _customTreeNames.Count; i++) { customTreeRoots.Add((BrowserDefinition)(((BrowserTree)_customTreeList[i])[_customTreeNames[i]])); } //create a CodeCompileUnit //add a CodeNamespace object to the CodeCompileUnit //add a CodeTypeDeclaration to the CodeNamespace //add all the members of the type/class to the CodeTypeDeclaration //use a CodeGenerator to generate code from the CodeCompileUnit //a CodeDomProvider can provide a CodeGenerator //translate the BrowserDefinition tree to code CSharpCodeProvider cscp = new CSharpCodeProvider(); // namespace System.Web.BrowserCapsFactory CodeCompileUnit ccu = new CodeCompileUnit(); //add strong-name key pair for CodeAttributeDeclaration declaration = new CodeAttributeDeclaration( "System.Reflection.AssemblyKeyFile", new CodeAttributeArgument[] { new CodeAttributeArgument(new CodePrimitiveExpression(_strongNameKeyFileName))}); CodeAttributeDeclaration aptca = new CodeAttributeDeclaration( "System.Security.AllowPartiallyTrustedCallers"); ccu.AssemblyCustomAttributes.Add(aptca); ccu.AssemblyCustomAttributes.Add(declaration); //add version number for it so it can distinguished in future versions declaration = new CodeAttributeDeclaration( "System.Reflection.AssemblyVersion", new CodeAttributeArgument[] { new CodeAttributeArgument(new CodePrimitiveExpression(ThisAssembly.Version))}); ccu.AssemblyCustomAttributes.Add(declaration); CodeNamespace cnamespace = new CodeNamespace("ASP"); //GEN: using System; cnamespace.Imports.Add(new CodeNamespaceImport("System")); //GEN: using System.Web; cnamespace.Imports.Add(new CodeNamespaceImport("System.Web")); //GEN: using System.Web.Configuration; cnamespace.Imports.Add(new CodeNamespaceImport("System.Web.Configuration")); //GEN: using System.Reflection; cnamespace.Imports.Add(new CodeNamespaceImport("System.Reflection")); //GEN: class BrowserCapabilitiesFactory ccu.Namespaces.Add(cnamespace); CodeTypeDeclaration factoryType = new CodeTypeDeclaration("BrowserCapabilitiesFactory"); factoryType.Attributes = MemberAttributes.Private; factoryType.IsClass = true; factoryType.Name = TypeName; factoryType.BaseTypes.Add(new CodeTypeReference("System.Web.Configuration.BrowserCapabilitiesFactoryBase")); cnamespace.Types.Add(factoryType); //GEN: protected override object ConfigureBrowserCapabilities(NameValueCollection headers, HttpBrowserCapabilities browserCaps) CodeMemberMethod method = new CodeMemberMethod(); method.Attributes = MemberAttributes.Override | MemberAttributes.Public; method.ReturnType = new CodeTypeReference(typeof(void)); method.Name = "ConfigureBrowserCapabilities"; CodeParameterDeclarationExpression cpde = new CodeParameterDeclarationExpression(typeof(NameValueCollection), _headersRefName); method.Parameters.Add(cpde); cpde = new CodeParameterDeclarationExpression(typeof(HttpBrowserCapabilities), browserCapsVariable); method.Parameters.Add(cpde); factoryType.Members.Add(method); GenerateSingleProcessCall(root, method); for (int i = 0; i < customTreeRoots.Count; i++) { GenerateSingleProcessCall((BrowserDefinition)customTreeRoots[i], method); } //GEN: if(this.IsBrowserUnknown(browserCaps) == false) return; CodeConditionStatement istatement = new CodeConditionStatement(); CodeMethodInvokeExpression cmie = new CodeMethodInvokeExpression(new CodeThisReferenceExpression(), "IsBrowserUnknown"); cmie.Parameters.Add(_browserCapsRefExpr); istatement.Condition = new CodeBinaryOperatorExpression(cmie, CodeBinaryOperatorType.ValueEquality, new CodePrimitiveExpression(false)); istatement.TrueStatements.Add(new CodeMethodReturnStatement()); method.Statements.Add(istatement); if(defaultRoot != null) { GenerateSingleProcessCall(defaultRoot, method, "Default"); } for (int i = 0; i < customTreeRoots.Count; i++) { foreach (DictionaryEntry entry in (BrowserTree)_customTreeList[i]) { BrowserDefinition bd = entry.Value as BrowserDefinition; Debug.Assert(bd != null); GenerateProcessMethod(bd, factoryType); } } //GenerateCallsToProcessMethods(root, method); foreach (DictionaryEntry entry in _browserTree) { BrowserDefinition bd = entry.Value as BrowserDefinition; Debug.Assert(bd != null); GenerateProcessMethod(bd, factoryType); } foreach (DictionaryEntry entry in _defaultTree) { BrowserDefinition bd = entry.Value as BrowserDefinition; Debug.Assert(bd != null); GenerateProcessMethod(bd, factoryType, "Default"); } GenerateOverrideMatchedHeaders(factoryType); GenerateOverrideBrowserElements(factoryType); //TODO: don't actually generate the code, just compile it in memory TextWriter twriter = new StreamWriter(new FileStream(_browsersDirectory + "\\BrowserCapsFactory.cs", FileMode.Create)); try { cscp.GenerateCodeFromCompileUnit(ccu, twriter, null); } finally { if(twriter != null) twriter.Close(); } CompilationSection compConfig = MTConfigUtil.GetCompilationAppConfig(); bool debug = compConfig.Debug; #if !PLATFORM_UNIX // File system paths must account for UNIX string strongNameFile = _browsersDirectory + "\\" + _strongNameKeyFileName; #else // !PLATFORM_UNIX string strongNameFile = _browsersDirectory + "/" + _strongNameKeyFileName; #endif // !PLATFORM_UNIX // Generate strong name file StrongNameUtility.GenerateStrongNameFile(strongNameFile); //TODO: do not use interim file: CompileAssemblyFromDom instead string[] referencedAssemblies = new string[2] { "System.dll", "System.Web.dll" }; CompilerParameters compilerParameters = new CompilerParameters(referencedAssemblies, "ASP.BrowserCapsFactory", debug /* includeDebugInformation */ ); compilerParameters.GenerateInMemory = false; compilerParameters.OutputAssembly = _browsersDirectory + "\\ASP.BrowserCapsFactory.dll"; CompilerResults results = null; try { results = cscp.CompileAssemblyFromFile(compilerParameters, _browsersDirectory + "\\BrowserCapsFactory.cs"); } finally { if (File.Exists(strongNameFile)) { File.Delete(strongNameFile); } } if (results.NativeCompilerReturnValue != 0 || results.Errors.HasErrors) { foreach (CompilerError error in results.Errors) { if (!error.IsWarning) { throw new HttpCompileException(error.ErrorText); } } throw new HttpCompileException(SR.GetString(SR.Browser_compile_error)); } Assembly resultAssembly = results.CompiledAssembly; GacUtil gacutil = new GacUtil(); gacutil.GacInstall(resultAssembly.Location); SavePublicKeyTokenFile(_publicKeyTokenFile, resultAssembly.GetName().GetPublicKeyToken()); }
internal bool UninstallInternal() { if (File.Exists(_publicKeyTokenFile)) { File.Delete(_publicKeyTokenFile); } GacUtil util = new GacUtil(); if (!util.GacUnInstall("ASP.BrowserCapsFactory, Version=4.0.0.0, Culture=neutral")) { return false; } return true; }
internal bool UninstallInternal() { // Remove existing strong name public token file if (File.Exists(_publicKeyTokenFile)) { File.Delete(_publicKeyTokenFile); } // Removing existing copy from GAC GacUtil gacutil = new GacUtil(); bool assemblyRemoved = gacutil.GacUnInstall("ASP.BrowserCapsFactory, Version=" + ThisAssembly.Version + ", Culture=neutral"); if (!assemblyRemoved) { return false; } return true; }