Exemple #1
0
        //This attempts to prevent the program from crashing if a plugin throws an exception.
        //It is a rather dirty approach and repeated calls will cause a memory leak.
        private void PreventPluginCrash(object sender, UnhandledExceptionEventArgs e)
        {
            StackTrace trace = new StackTrace((Exception)e.ExceptionObject);

            foreach (StackFrame frame in trace.GetFrames())
            {
                Assembly frameAssembly = frame.GetMethod().DeclaringType.Assembly;
                if (Plugins.ContainsKey(frameAssembly.GetName().Name))
                {
                    IMSPluginBase plugin = Plugins[frameAssembly.GetName().Name];
                    Logger.WriteError("An uncaught exception was raised in plugin " + plugin.Name + "!  The plugin has been disabled.  Error:\n" + e.ExceptionObject);
                    try
                    {
                        plugin.Stop();
                    }
                    catch (Exception stopException)
                    {
                        Logger.WriteError("During fatal error unload, the plugin's stop method also failed.  Exception:\n" + stopException);
                    }
                    Plugins.Remove(plugin.Name);
                    KnownPlugins[plugin.PluginAssembly.GetName().Name].Enabled = false;
                    Thread.CurrentThread.IsBackground = true;
                    Thread.CurrentThread.Join(); //suspend the thread indefinitely to stop the CLR from shutting down
                }
            }
            Logger.WriteError("A fatal error occured, resulting in IMS shutting down!\n" + e.ExceptionObject);
        }
Exemple #2
0
        /// <summary>
        /// Attempts to load a plugin into memory from the specified path.
        /// </summary>
        /// <param name="path">The path of the plugin to load.</param>
        /// <returns>The loaded plugin.</returns>
        public IMSPluginBase LoadPlugin(string path)
        {
            IMSPluginBase plugin = LoadPluginAssembly(path);

            plugin.Start();
            return(plugin);
        }
Exemple #3
0
 /// <summary>
 /// Creates a new instance of the plugin information class using the given plugin.
 /// </summary>
 /// <param name="plugin">The plugin to gather information about.</param>
 public PluginInformation(IMSPluginBase plugin)
 {
     Name            = plugin.Name;
     Author          = plugin.Author;
     Description     = plugin.Description;
     AssemblyName    = plugin.PluginAssemblyName;
     FileName        = plugin.PluginAssembly.Location;
     AssemblyVersion = plugin.CurrentVersion;
     Enabled         = true;
 }
Exemple #4
0
 /// <summary>
 /// Attempts to remove a plugin from memory.  This does not guarantee that the plugin's assembly will be unloaded.
 /// </summary>
 /// <param name="plugin">The plugin to unload.</param>
 public void UnloadPlugin(IMSPluginBase plugin)
 {
     lock (Locker)
         if (Plugins.ContainsKey(plugin.PluginAssemblyName))
         {
             plugin.Stop();
             Plugins.Remove(plugin.PluginAssemblyName);
         }
         else
         {
             throw new ArgumentException("This plugin object has not been loaded by the plugin manager.");
         }
 }
Exemple #5
0
 private IMSPluginBase LoadPluginAssembly(string path)
 {
     lock (Locker)
     {
         AssemblyLoadContext context        = new AssemblyLoadContext(null, true);
         Assembly            pluginAssembly = context.LoadFromAssemblyPath(path);
         try
         {
             IMSPluginBase plugin = (IMSPluginBase)Activator.CreateInstance(pluginAssembly.GetTypes().Where(x => x.BaseType == typeof(IMSPluginBase)).Single());
             Plugins[plugin.PluginAssemblyName]      = plugin;
             KnownPlugins[plugin.PluginAssemblyName] = new PluginInformation(plugin);
             return(plugin);
         }
         finally
         {
             context.Unload(); //start context unload now so the assembly disappears once the plugin is gc'd
         }
     }
 }