static ShipLoader GetShipFromAssembly(Assembly assembly) { ShipLoader rv = null; FileIOPermission permission = new FileIOPermission(PermissionState.Unrestricted); permission.AllFiles = FileIOPermissionAccess.AllAccess; permission.Deny(); bool isUsed = false; foreach (Type type in assembly.GetTypes()) { if (!type.IsAbstract && type.IsPublic && (type.IsSubclassOf(typeof(ShipLoader)) || type == typeof(ShipLoader))) { rv = (ShipLoader)(type.GetConstructor(Type.EmptyTypes).Invoke(null)); break; } } if (isUsed) { if (assemblies == null) { assemblies = new List <Assembly>(); System.AppDomain.CurrentDomain.AssemblyResolve += new ResolveEventHandler(AssemblyResolve); } assemblies.Add(assembly); } return(rv); }
public static List <ShipLoader> GetShips() { List <ShipLoader> returnvalues = new List <ShipLoader>(); DirectoryInfo info = new DirectoryInfo(SuperMeleePaths.ShipDir); if (info.Exists) { string AssemblyInfoPath = Path.GetTempFileName(); File.WriteAllLines(AssemblyInfoPath, AssemblyInfo); CompilerParameters parameters = new CompilerParameters(assemblyNames); foreach (DirectoryInfo dirinfo in info.GetDirectories()) { FileInfo[] fileinfos = dirinfo.GetFiles("*.cs"); if (fileinfos.Length > 0) { #if Release try { #endif string sourceFile = fileinfos[0].FullName; string directory = dirinfo.FullName + Path.DirectorySeparatorChar; string shipsName = dirinfo.Name.Replace(Path.DirectorySeparatorChar, '.'); string infoFile = directory + "CompiledInfo.txt"; string binFile = directory + shipsName + ".dll"; string errorFile = directory + "CompilerErrors.txt"; string configFile = directory + ShipLoader.ConfigFileName; /*string infoFile = Path.ChangeExtension(sourceFile, ".CompiledInfo.txt"); * string binFile = Path.ChangeExtension(sourceFile, ".dll"); * string errorFile = Path.ChangeExtension(sourceFile, ".Error.txt");*/ if (File.Exists(infoFile)) { Console.WriteLine("Loading " + shipsName); try { string[] CompiledInfo = File.ReadAllLines(infoFile); if (CompiledInfo.Length > 0 && File.Exists(binFile) && CompiledInfo[0] == GetHash(sourceFile, binFile)) { ShipLoader loader = GetShipFromAssembly(Assembly.LoadFile(binFile)); loader.ShipDirectory = dirinfo.FullName + Path.DirectorySeparatorChar; returnvalues.Add(loader); continue; } } catch (UnauthorizedAccessException) { } Console.WriteLine("Loading Failed"); File.Delete(infoFile); } if (CheckNamespaceUse(sourceFile, errorFile)) { Console.WriteLine("Compiling " + shipsName); parameters.OutputAssembly = binFile; if (File.Exists(binFile)) { File.Delete(binFile); } if (File.Exists(configFile)) { File.Delete(configFile); } string[] paths = new string[fileinfos.Length + 1]; paths[0] = AssemblyInfoPath; for (int pos = 0; pos < fileinfos.Length; ++pos) { paths[pos + 1] = fileinfos[pos].FullName; } CompilerResults results = provider.CompileAssemblyFromFile(parameters, paths); if (results.Errors.Count > 0) { using (StreamWriter writer = new StreamWriter(errorFile)) { foreach (CompilerError error in results.Errors) { writer.WriteLine("{0} {1} Description: {2} File: {3} Line: {4} Column: {5}", (error.IsWarning) ? ("Warning") : ("Error"), error.ErrorNumber, error.ErrorText, error.FileName, error.Line, error.Column); } } continue; } ShipLoader loader = GetShipFromAssembly(results.CompiledAssembly); loader.ShipDirectory = dirinfo.FullName + Path.DirectorySeparatorChar; returnvalues.Add(loader); File.WriteAllLines(infoFile, new string[] { GetHash(sourceFile, binFile) }); File.SetAttributes(infoFile, File.GetAttributes(infoFile) | FileAttributes.Hidden); File.SetAttributes(binFile, File.GetAttributes(binFile) | FileAttributes.Hidden); if (File.Exists(errorFile)) { File.Delete(errorFile); } } #if Release } catch (Exception ex) { ErrorBox.DisplayError(ex); } #endif } } File.Delete(AssemblyInfoPath); } return(returnvalues); }