Added --force-video-library command line option

This feature will allow users to bypass the automatic driver detection functionality so that they can at least force  the use of the built-in Windows driver if NVIDIA or AMD ever have an issue with their drivers.
This commit is contained in:
Terry MacDonald 2021-09-02 13:47:28 +12:00
parent 9cef45416e
commit 65bbd1ab66
3 changed files with 217 additions and 46 deletions

View File

@ -235,10 +235,12 @@ namespace DisplayMagician {
CommandOption debug = app.Option("--debug", "Generate a DisplayMagician.log debug-level log file", CommandOptionType.NoValue); CommandOption debug = app.Option("--debug", "Generate a DisplayMagician.log debug-level log file", CommandOptionType.NoValue);
CommandOption trace = app.Option("--trace", "Generate a DisplayMagician.log trace-level log file", CommandOptionType.NoValue); CommandOption trace = app.Option("--trace", "Generate a DisplayMagician.log trace-level log file", CommandOptionType.NoValue);
CommandOption forcedVideoLibrary = app.Option("--force-video-library", "Bypass the normal video detection logic to force a particular video library (AMD, NVIDIA, Windows)", CommandOptionType.SingleValue);
// This is the RunShortcut command // This is the RunShortcut command
app.Command(DisplayMagicianStartupAction.RunShortcut.ToString(), (runShortcutCmd) => app.Command(DisplayMagicianStartupAction.RunShortcut.ToString(), (runShortcutCmd) =>
{ {
// Set the --trace or --debug options if supplied
if (trace.HasValue()) if (trace.HasValue())
{ {
Console.WriteLine($"Changing logging level to TRACE level as --trace was provided on the commandline."); Console.WriteLine($"Changing logging level to TRACE level as --trace was provided on the commandline.");
@ -254,6 +256,29 @@ namespace DisplayMagician {
NLog.LogManager.ReconfigExistingLoggers(); NLog.LogManager.ReconfigExistingLoggers();
} }
// Set the --force-video-library option if supplied
if (forcedVideoLibrary.HasValue())
{
if (forcedVideoLibrary.Value().Equals("NVIDIA"))
{
ProfileRepository.ForcedVideoMode = FORCED_VIDEO_MODE.NVIDIA;
Console.WriteLine($"Forcing NVIDIA Video Library as '--force-video-library NVIDIA' was provided on the commandline.");
logger.Info($"Forcing NVIDIA Video Library as '--force-video-library NVIDIA' was provided on the commandline.");
}
else if (forcedVideoLibrary.Value().Equals("AMD"))
{
ProfileRepository.ForcedVideoMode = FORCED_VIDEO_MODE.AMD;
Console.WriteLine($"Forcing AMD Video Library as '--force-video-library AMD' was provided on the commandline.");
logger.Info($"Forcing AMD Video Library as '--force-video-library AMD' was provided on the commandline.");
}
else if (forcedVideoLibrary.Value().Equals("Windows"))
{
ProfileRepository.ForcedVideoMode = FORCED_VIDEO_MODE.WINDOWS;
Console.WriteLine($"Forcing Windows CCD Video Library as '--force-video-library Windows' was provided on the commandline.");
logger.Info($"Forcing Windows CCD Video Library as '--force-video-library Windows' was provided on the commandline.");
}
}
var argumentShortcut = runShortcutCmd.Argument("\"SHORTCUT_UUID\"", "(required) The UUID of the shortcut to run from those stored in the shortcut library.").IsRequired(); var argumentShortcut = runShortcutCmd.Argument("\"SHORTCUT_UUID\"", "(required) The UUID of the shortcut to run from those stored in the shortcut library.").IsRequired();
argumentShortcut.Validators.Add(new ShortcutMustExistValidator()); argumentShortcut.Validators.Add(new ShortcutMustExistValidator());
@ -273,6 +298,7 @@ namespace DisplayMagician {
// This is the ChangeProfile command // This is the ChangeProfile command
app.Command(DisplayMagicianStartupAction.ChangeProfile.ToString(), (runProfileCmd) => app.Command(DisplayMagicianStartupAction.ChangeProfile.ToString(), (runProfileCmd) =>
{ {
// Set the --trace or --debug options if supplied
if (trace.HasValue()) if (trace.HasValue())
{ {
Console.WriteLine($"Changing logging level to TRACE level as --trace was provided on the commandline."); Console.WriteLine($"Changing logging level to TRACE level as --trace was provided on the commandline.");
@ -288,6 +314,29 @@ namespace DisplayMagician {
NLog.LogManager.ReconfigExistingLoggers(); NLog.LogManager.ReconfigExistingLoggers();
} }
// Set the --force-video-library option if supplied
if (forcedVideoLibrary.HasValue())
{
if (forcedVideoLibrary.Value().Equals("NVIDIA"))
{
ProfileRepository.ForcedVideoMode = FORCED_VIDEO_MODE.NVIDIA;
Console.WriteLine($"Forcing NVIDIA Video Library as '--force-video-library NVIDIA' was provided on the commandline.");
logger.Info($"Forcing NVIDIA Video Library as '--force-video-library NVIDIA' was provided on the commandline.");
}
else if (forcedVideoLibrary.Value().Equals("AMD"))
{
ProfileRepository.ForcedVideoMode = FORCED_VIDEO_MODE.AMD;
Console.WriteLine($"Forcing AMD Video Library as '--force-video-library AMD' was provided on the commandline.");
logger.Info($"Forcing AMD Video Library as '--force-video-library AMD' was provided on the commandline.");
}
else if (forcedVideoLibrary.Value().Equals("Windows"))
{
ProfileRepository.ForcedVideoMode = FORCED_VIDEO_MODE.WINDOWS;
Console.WriteLine($"Forcing Windows CCD Video Library as '--force-video-library Windows' was provided on the commandline.");
logger.Info($"Forcing Windows CCD Video Library as '--force-video-library Windows' was provided on the commandline.");
}
}
var argumentProfile = runProfileCmd.Argument("\"Profile_UUID\"", "(required) The UUID of the profile to run from those stored in the profile file.").IsRequired(); var argumentProfile = runProfileCmd.Argument("\"Profile_UUID\"", "(required) The UUID of the profile to run from those stored in the profile file.").IsRequired();
argumentProfile.Validators.Add(new ProfileMustExistValidator()); argumentProfile.Validators.Add(new ProfileMustExistValidator());
@ -314,6 +363,7 @@ namespace DisplayMagician {
// This is the CreateProfile command // This is the CreateProfile command
app.Command(DisplayMagicianStartupAction.CreateProfile.ToString(), (createProfileCmd) => app.Command(DisplayMagicianStartupAction.CreateProfile.ToString(), (createProfileCmd) =>
{ {
// Set the --trace or --debug options if supplied
if (trace.HasValue()) if (trace.HasValue())
{ {
Console.WriteLine($"Changing logging level to TRACE level as --trace was provided on the commandline."); Console.WriteLine($"Changing logging level to TRACE level as --trace was provided on the commandline.");
@ -329,6 +379,29 @@ namespace DisplayMagician {
NLog.LogManager.ReconfigExistingLoggers(); NLog.LogManager.ReconfigExistingLoggers();
} }
// Set the --force-video-library option if supplied
if (forcedVideoLibrary.HasValue())
{
if (forcedVideoLibrary.Value().Equals("NVIDIA"))
{
ProfileRepository.ForcedVideoMode = FORCED_VIDEO_MODE.NVIDIA;
Console.WriteLine($"Forcing NVIDIA Video Library as '--force-video-library NVIDIA' was provided on the commandline.");
logger.Info($"Forcing NVIDIA Video Library as '--force-video-library NVIDIA' was provided on the commandline.");
}
else if (forcedVideoLibrary.Value().Equals("AMD"))
{
ProfileRepository.ForcedVideoMode = FORCED_VIDEO_MODE.AMD;
Console.WriteLine($"Forcing AMD Video Library as '--force-video-library AMD' was provided on the commandline.");
logger.Info($"Forcing AMD Video Library as '--force-video-library AMD' was provided on the commandline.");
}
else if (forcedVideoLibrary.Value().Equals("Windows"))
{
ProfileRepository.ForcedVideoMode = FORCED_VIDEO_MODE.WINDOWS;
Console.WriteLine($"Forcing Windows CCD Video Library as '--force-video-library Windows' was provided on the commandline.");
logger.Info($"Forcing Windows CCD Video Library as '--force-video-library Windows' was provided on the commandline.");
}
}
//description and help text of the command. //description and help text of the command.
createProfileCmd.Description = "Use this command to go directly to the create display profile screen."; createProfileCmd.Description = "Use this command to go directly to the create display profile screen.";
@ -343,6 +416,7 @@ namespace DisplayMagician {
app.OnExecute(() => app.OnExecute(() =>
{ {
// Set the --trace or --debug options if supplied
if (trace.HasValue()) if (trace.HasValue())
{ {
Console.WriteLine($"Changing logging level to TRACE level as --trace was provided on the commandline."); Console.WriteLine($"Changing logging level to TRACE level as --trace was provided on the commandline.");
@ -358,6 +432,29 @@ namespace DisplayMagician {
NLog.LogManager.ReconfigExistingLoggers(); NLog.LogManager.ReconfigExistingLoggers();
} }
// Set the --force-video-library option if supplied
if (forcedVideoLibrary.HasValue())
{
if (forcedVideoLibrary.Value().Equals("NVIDIA"))
{
ProfileRepository.ForcedVideoMode = FORCED_VIDEO_MODE.NVIDIA;
Console.WriteLine($"Forcing NVIDIA Video Library as '--force-video-library NVIDIA' was provided on the commandline.");
logger.Info($"Forcing NVIDIA Video Library as '--force-video-library NVIDIA' was provided on the commandline.");
}
else if (forcedVideoLibrary.Value().Equals("AMD"))
{
ProfileRepository.ForcedVideoMode = FORCED_VIDEO_MODE.AMD;
Console.WriteLine($"Forcing AMD Video Library as '--force-video-library AMD' was provided on the commandline.");
logger.Info($"Forcing AMD Video Library as '--force-video-library AMD' was provided on the commandline.");
}
else if (forcedVideoLibrary.Value().Equals("Windows"))
{
ProfileRepository.ForcedVideoMode = FORCED_VIDEO_MODE.WINDOWS;
Console.WriteLine($"Forcing Windows CCD Video Library as '--force-video-library Windows' was provided on the commandline.");
logger.Info($"Forcing Windows CCD Video Library as '--force-video-library Windows' was provided on the commandline.");
}
}
logger.Debug($"No commandline command was invoked, so starting up normally"); logger.Debug($"No commandline command was invoked, so starting up normally");
// Add a workaround to handle the weird way that Windows tell us that DisplayMagician // Add a workaround to handle the weird way that Windows tell us that DisplayMagician
// was started from a Notification Toast when closed (Windows 10) // was started from a Notification Toast when closed (Windows 10)

View File

@ -164,19 +164,25 @@ namespace DisplayMagicianShared.NVIDIA
public override void RefreshPossbility() public override void RefreshPossbility()
{ {
// Check whether this profile is possible // Check whether this profile is possible
if (NVIDIALibrary.GetLibrary().IsPossibleConfig(_nvidiaDisplayConfig)) if (ProfileRepository.CurrentVideoMode == VIDEO_MODE.NVIDIA && NVIDIALibrary.GetLibrary().IsInstalled)
{ {
if (NVIDIALibrary.GetLibrary().IsPossibleConfig(_nvidiaDisplayConfig))
{
SharedLogger.logger.Debug($"ProfileRepository/IsPossibleRefresh: The NVIDIA profile {Name} is possible!"); SharedLogger.logger.Debug($"ProfileRepository/IsPossibleRefresh: The NVIDIA profile {Name} is possible!");
_isPossible = true; _isPossible = true;
}
else
{
SharedLogger.logger.Debug($"ProfileRepository/IsPossibleRefresh: The NVIDIA profile {Name} is NOT possible!");
_isPossible = false;
}
} }
else else
{ {
SharedLogger.logger.Debug($"ProfileRepository/IsPossibleRefresh: The NVIDIA profile {Name} is NOT possible!");
_isPossible = false; _isPossible = false;
} }
} }
// Actually set this profile active // Actually set this profile active

View File

@ -25,6 +25,14 @@ namespace DisplayMagicianShared
AMD = 2, AMD = 2,
} }
public enum FORCED_VIDEO_MODE : Int32
{
WINDOWS = 0,
NVIDIA = 1,
AMD = 2,
DETECT = 99,
}
public enum ApplyProfileResult public enum ApplyProfileResult
{ {
Successful, Successful,
@ -46,8 +54,9 @@ namespace DisplayMagicianShared
private static AMDLibrary amdLibrary; private static AMDLibrary amdLibrary;
private static NVIDIALibrary nvidiaLibrary; private static NVIDIALibrary nvidiaLibrary;
private static WinLibrary winLibrary; private static WinLibrary winLibrary;
// Make th default video mode Windows // Make the default video mode Windows
public static VIDEO_MODE _currentVideoMode = VIDEO_MODE.WINDOWS; private static VIDEO_MODE _currentVideoMode = VIDEO_MODE.WINDOWS;
private static FORCED_VIDEO_MODE _forcedVideoMode = FORCED_VIDEO_MODE.DETECT;
// Other constants that are useful // Other constants that are useful
public static string AppDataPath = System.IO.Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), "DisplayMagician"); public static string AppDataPath = System.IO.Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), "DisplayMagician");
@ -55,6 +64,7 @@ namespace DisplayMagicianShared
public static string AppDisplayMagicianIconFilename = System.IO.Path.Combine(AppIconPath, @"DisplayMagician.ico"); public static string AppDisplayMagicianIconFilename = System.IO.Path.Combine(AppIconPath, @"DisplayMagician.ico");
private static readonly string AppProfileStoragePath = System.IO.Path.Combine(AppDataPath, $"Profiles"); private static readonly string AppProfileStoragePath = System.IO.Path.Combine(AppDataPath, $"Profiles");
private static readonly string _profileStorageJsonFileName = System.IO.Path.Combine(AppProfileStoragePath, $"DisplayProfiles_{_version.ToString(2)}.json"); private static readonly string _profileStorageJsonFileName = System.IO.Path.Combine(AppProfileStoragePath, $"DisplayProfiles_{_version.ToString(2)}.json");
#endregion #endregion
@ -62,41 +72,7 @@ namespace DisplayMagicianShared
#region Class Constructors #region Class Constructors
static ProfileRepository() static ProfileRepository()
{ {
// Figure out the Video Cards and see what mode we want
// Get a list of all the PCI Vendor IDs
List<string> videoCardVendors = WinLibrary.GetLibrary().GetCurrentPCIVideoCardVendors();
// This sets the order in which the different modes have been chosen.
// NVIDIA Video cards are the most common, so go first
_currentVideoMode = VIDEO_MODE.WINDOWS;
if (NVIDIALibrary.GetLibrary().PCIVendorIDs.All(value => videoCardVendors.Contains(value)))
{
// Initialise the the NVIDIA NvAPI Library
try
{
SharedLogger.logger.Debug($"ProfileRepository/ProfileRepository: Initialising the NVIDIA NVAPI library.");
nvidiaLibrary = new NVIDIALibrary();
_currentVideoMode = VIDEO_MODE.NVIDIA;
}
catch (Exception ex)
{
SharedLogger.logger.Warn(ex, $"ProfileRepository/ProfileRepository: Initialising NVIDIA NVAPI caused an exception.");
}
}
else if (AMDLibrary.GetLibrary().PCIVendorIDs.All(value => videoCardVendors.Contains(value)))
{
// Initialise the the AMD ADL Library
try
{
SharedLogger.logger.Debug($"ProfileRepository/ProfileRepository: Initialising the AMD ADL library.");
amdLibrary = new AMDLibrary();
_currentVideoMode = VIDEO_MODE.AMD;
}
catch (Exception ex)
{
SharedLogger.logger.Warn(ex, $"ProfileRepository/ProfileRepository: Initialising AMD ADL caused an exception.");
}
}
try try
{ {
// Create the Profile Storage Path if it doesn't exist so that it's avilable for all the program // Create the Profile Storage Path if it doesn't exist so that it's avilable for all the program
@ -199,6 +175,18 @@ namespace DisplayMagicianShared
_currentVideoMode = value; _currentVideoMode = value;
} }
} }
public static FORCED_VIDEO_MODE ForcedVideoMode
{
get
{
return _forcedVideoMode;
}
set
{
_forcedVideoMode = value;
SetVideoCardMode(value);
}
}
public static List<string> ConnectedDisplayIdentifiers public static List<string> ConnectedDisplayIdentifiers
@ -924,11 +912,11 @@ namespace DisplayMagicianShared
public static List<string> GetAllConnectedDisplayIdentifiers() public static List<string> GetAllConnectedDisplayIdentifiers()
{ {
if (NVIDIALibrary.GetLibrary().IsInstalled) if (_currentVideoMode == VIDEO_MODE.NVIDIA && NVIDIALibrary.GetLibrary().IsInstalled)
{ {
return NVIDIALibrary.GetLibrary().GetAllConnectedDisplayIdentifiers(); return NVIDIALibrary.GetLibrary().GetAllConnectedDisplayIdentifiers();
} }
else if (AMDLibrary.GetLibrary().IsInstalled) else if (_currentVideoMode == VIDEO_MODE.AMD && AMDLibrary.GetLibrary().IsInstalled)
{ {
return AMDLibrary.GetLibrary().GetAllConnectedDisplayIdentifiers(); return AMDLibrary.GetLibrary().GetAllConnectedDisplayIdentifiers();
} }
@ -940,11 +928,11 @@ namespace DisplayMagicianShared
public static List<string> GetCurrentDisplayIdentifiers() public static List<string> GetCurrentDisplayIdentifiers()
{ {
if (NVIDIALibrary.GetLibrary().IsInstalled) if (_currentVideoMode == VIDEO_MODE.NVIDIA && NVIDIALibrary.GetLibrary().IsInstalled)
{ {
return NVIDIALibrary.GetLibrary().GetCurrentDisplayIdentifiers(); return NVIDIALibrary.GetLibrary().GetCurrentDisplayIdentifiers();
} }
else if (AMDLibrary.GetLibrary().IsInstalled) else if (_currentVideoMode == VIDEO_MODE.AMD && AMDLibrary.GetLibrary().IsInstalled)
{ {
return AMDLibrary.GetLibrary().GetCurrentDisplayIdentifiers(); return AMDLibrary.GetLibrary().GetCurrentDisplayIdentifiers();
} }
@ -1093,6 +1081,86 @@ namespace DisplayMagicianShared
return ApplyProfileResult.Successful; return ApplyProfileResult.Successful;
} }
public static bool SetVideoCardMode(FORCED_VIDEO_MODE forcedVideoMode = FORCED_VIDEO_MODE.DETECT)
{
_forcedVideoMode = forcedVideoMode;
// This sets the order in which the different modes have been chosen.
// NVIDIA Video cards are the most common, so go first
if (_forcedVideoMode == FORCED_VIDEO_MODE.NVIDIA)
{
// We force the video mode to be NVIDIA
_currentVideoMode = VIDEO_MODE.NVIDIA;
}
else if (forcedVideoMode == FORCED_VIDEO_MODE.AMD)
{
// We force the video mode to be AMD
_currentVideoMode = VIDEO_MODE.AMD;
}
else if (forcedVideoMode == FORCED_VIDEO_MODE.WINDOWS)
{
// We force the video mode to be WINDOWS
_currentVideoMode = VIDEO_MODE.WINDOWS;
}
else
{
// We do normal video library detection based on the video card!
// Figure out the Video Cards and see what mode we want
// Get a list of all the PCI Vendor IDs
List<string> videoCardVendors = WinLibrary.GetLibrary().GetCurrentPCIVideoCardVendors();
if (NVIDIALibrary.GetLibrary().PCIVendorIDs.All(value => videoCardVendors.Contains(value)))
{
// We detected a NVIDIA video card in the computer
_currentVideoMode = VIDEO_MODE.NVIDIA;
}
else if (AMDLibrary.GetLibrary().PCIVendorIDs.All(value => videoCardVendors.Contains(value)))
{
// We detected an AMD video card in the computer
_currentVideoMode = VIDEO_MODE.AMD;
}
else
{
// We fallback to the built-in Windows CCD drivers
_currentVideoMode = VIDEO_MODE.WINDOWS;
}
}
if (_currentVideoMode == VIDEO_MODE.NVIDIA)
{
// Initialise the the NVIDIA NvAPI Library
try
{
SharedLogger.logger.Debug($"ProfileRepository/ProfileRepository: Initialising the NVIDIA NVAPI library.");
nvidiaLibrary = new NVIDIALibrary();
_currentVideoMode = VIDEO_MODE.NVIDIA;
}
catch (Exception ex)
{
SharedLogger.logger.Warn(ex, $"ProfileRepository/ProfileRepository: Initialising NVIDIA NVAPI caused an exception.");
return false;
}
}
else if (_currentVideoMode == VIDEO_MODE.AMD)
{
// Initialise the the AMD ADL Library
try
{
SharedLogger.logger.Debug($"ProfileRepository/ProfileRepository: Initialising the AMD ADL library.");
amdLibrary = new AMDLibrary();
_currentVideoMode = VIDEO_MODE.AMD;
}
catch (Exception ex)
{
SharedLogger.logger.Warn(ex, $"ProfileRepository/ProfileRepository: Initialising AMD ADL caused an exception.");
return false;
}
}
return true;
}
#endregion #endregion
} }