Fixed: added some additional boilerplate to FileLockChecker.CheckFile.

This commit is contained in:
MaxED 2016-06-26 00:48:10 +00:00 committed by spherallic
parent 41fc4d97c8
commit 8f74ff048e
2 changed files with 84 additions and 71 deletions

View file

@ -153,8 +153,7 @@ namespace CodeImp.DoomBuilder
{ {
result.Processes = new List<Process>((int)pnProcInfo); result.Processes = new List<Process>((int)pnProcInfo);
// Enumerate all of the results and add them to the // Enumerate all of the results and add them to the list to be returned
// list to be returned
for(int i = 0; i < pnProcInfo; i++) for(int i = 0; i < pnProcInfo; i++)
{ {
try try
@ -175,22 +174,29 @@ namespace CodeImp.DoomBuilder
foreach(Process process in result.Processes) foreach(Process process in result.Processes)
{ {
result.Error += Path.GetFileName(process.MainModule.FileName) string processpath = string.Empty;
+ " (\"" + process.MainModule.FileName try
+ "\", started at " + process.StartTime + ")" {
+ Environment.NewLine + Environment.NewLine; // All manner of exceptions are possible here...
processpath = process.MainModule.FileName;
}catch {}
result.Error += process.ProcessName
+ " (" + (!string.IsNullOrEmpty(processpath) ? "\"" + processpath + "\"" : "")
+ ", started at " + process.StartTime + ")"
+ Environment.NewLine;
} }
} }
} }
else else
{ {
result.Error = "Error " + res + ". Could not list processes locking resource."; //mxd result.Error = "Error " + res + ". Could not list processes locking the resource."; //mxd
return result; return result;
} }
} }
else if(res != 0) else if(res != 0)
{ {
result.Error = "Error " + res + ". Could not list processes locking resource. Failed to get size of result."; //mxd result.Error = "Error " + res + ". Could not list processes locking resource. Failed to get result size."; //mxd
return result; return result;
} }
} }

View file

@ -746,21 +746,22 @@ namespace CodeImp.DoomBuilder
string settingsfile; string settingsfile;
WAD targetwad = null; WAD targetwad = null;
bool includenodes; bool includenodes;
bool fileexists = File.Exists(newfilepathname); //mxd
General.WriteLogLine("Saving map to file: " + newfilepathname); General.WriteLogLine("Saving map to file: " + newfilepathname);
//mxd. Official IWAD check... //mxd. Official IWAD check...
WAD hashtest = new WAD(newfilepathname, true); if(fileexists)
if(hashtest.IsOfficialIWAD)
{
General.WriteLogLine("Map saving aborted: attempt to modify official IWAD");
General.ShowErrorMessage("Official IWADs should not be modified.\nConsider making a PWAD instead", MessageBoxButtons.OK);
return false;
}
else
{ {
WAD hashtest = new WAD(newfilepathname, true);
if(hashtest.IsOfficialIWAD)
{
General.WriteLogLine("Map saving aborted: attempt to modify an official IWAD");
General.ShowErrorMessage("Official IWADs should not be modified.\nConsider making a PWAD instead", MessageBoxButtons.OK);
return false;
}
hashtest.Dispose(); hashtest.Dispose();
hashtest = null;
} }
// Scripts changed? // Scripts changed?
@ -769,9 +770,9 @@ namespace CodeImp.DoomBuilder
// If the scripts window is open, save the scripts first // If the scripts window is open, save the scripts first
if(IsScriptsWindowOpen) scriptwindow.Editor.ImplicitSave(); if(IsScriptsWindowOpen) scriptwindow.Editor.ImplicitSave();
// Only recompile scripts when the scripts have changed // Only recompile scripts when the scripts have changed or there are compiler errors (mxd)
// (not when only the map changed) // (not when only the map changed)
if(localscriptschanged && !CompileScriptLumps()) if((localscriptschanged || errors.Count > 0) && !CompileScriptLumps())
{ {
// Compiler failure // Compiler failure
if(errors.Count > 0) if(errors.Count > 0)
@ -808,79 +809,85 @@ namespace CodeImp.DoomBuilder
} }
//mxd. Target file is read-only? //mxd. Target file is read-only?
FileInfo info = new FileInfo(newfilepathname); if(fileexists)
if(info.Exists && info.IsReadOnly)
{ {
if(General.ShowWarningMessage("Unable to save the map: target file is read-only.\nRemove read-only flag and save the map anyway?", MessageBoxButtons.YesNo) == DialogResult.Yes) FileInfo info = new FileInfo(newfilepathname);
if(info.IsReadOnly)
{ {
General.WriteLogLine("Removing read-only flag from the map file..."); if(General.ShowWarningMessage("Unable to save the map: target file is read-only.\nRemove read-only flag and save the map anyway?", MessageBoxButtons.YesNo) == DialogResult.Yes)
try
{ {
info.IsReadOnly = false; General.WriteLogLine("Removing read-only flag from the map file...");
try
{
info.IsReadOnly = false;
}
catch(Exception e)
{
General.ShowErrorMessage("Failed to remove read-only flag from \"" + filepathname + "\":" + Environment.NewLine + Environment.NewLine + e.Message, MessageBoxButtons.OK);
General.WriteLogLine("Failed to remove read-only flag from \"" + filepathname + "\":" + e.Message);
return false;
}
} }
catch(Exception e) else
{ {
General.ShowErrorMessage("Failed to remove read-only flag from \"" + filepathname + "\":" + Environment.NewLine + Environment.NewLine + e.Message, MessageBoxButtons.OK); General.WriteLogLine("Map saving cancelled...");
General.WriteLogLine("Failed to remove read-only flag from \"" + filepathname + "\":" + e.Message);
return false; return false;
} }
} }
else
{
General.WriteLogLine("Map saving cancelled...");
return false;
}
} }
// Suspend data resources // Suspend data resources
data.Suspend(); data.Suspend();
//mxd. Check if the target file is locked //mxd. Check if the target file is locked
FileLockChecker.FileLockCheckResult checkresult = FileLockChecker.CheckFile(newfilepathname); if(fileexists)
if(!string.IsNullOrEmpty(checkresult.Error))
{ {
if(checkresult.Processes.Count > 0) FileLockChecker.FileLockCheckResult checkresult = FileLockChecker.CheckFile(newfilepathname);
if(!string.IsNullOrEmpty(checkresult.Error))
{ {
string rest = "Press 'Retry' to close " + (checkresult.Processes.Count > 1 ? "all processes" : "the process") if(checkresult.Processes.Count > 0)
+ " and retry." + Environment.NewLine + "Press 'Cancel' to cancel saving.";
if(General.ShowErrorMessage(checkresult.Error + rest, MessageBoxButtons.RetryCancel) == DialogResult.Retry)
{ {
// Close all processes string rest = Environment.NewLine + "Press 'Retry' to close " + (checkresult.Processes.Count > 1 ? "all processes" : "the process")
foreach(Process process in checkresult.Processes) + " and retry." + Environment.NewLine + "Press 'Cancel' to cancel saving.";
{
try
{
if(!process.HasExited) process.Kill();
}
catch(Exception e)
{
General.ShowErrorMessage("Failed to close " + Path.GetFileName(process.MainModule.FileName) + ":" + Environment.NewLine + Environment.NewLine + e.Message, MessageBoxButtons.OK);
data.Resume();
General.WriteLogLine("Map saving failed: failed to close " + Path.GetFileName(process.MainModule.FileName));
return false;
}
}
// Retry if(General.ShowErrorMessage(checkresult.Error + rest, MessageBoxButtons.RetryCancel) == DialogResult.Retry)
data.Resume(); {
General.WriteLogLine("Map saving restarted..."); // Close all processes
return SaveMap(newfilepathname, purpose); foreach(Process process in checkresult.Processes)
{
try
{
if(!process.HasExited) process.Kill();
}
catch(Exception e)
{
General.ShowErrorMessage("Failed to close " + Path.GetFileName(process.MainModule.FileName) + ":" + Environment.NewLine + Environment.NewLine + e.Message, MessageBoxButtons.OK);
data.Resume();
General.WriteLogLine("Map saving failed: failed to close " + Path.GetFileName(process.MainModule.FileName));
return false;
}
}
// Retry
data.Resume();
General.WriteLogLine("Map saving restarted...");
return SaveMap(newfilepathname, purpose);
}
else
{
data.Resume();
General.WriteLogLine("Map saving cancelled...");
return false;
}
} }
else else
{ {
General.ShowErrorMessage(checkresult.Error, MessageBoxButtons.OK);
data.Resume(); data.Resume();
General.WriteLogLine("Map saving cancelled..."); General.WriteLogLine("Map saving failed: " + checkresult.Error);
return false; return false;
} }
} }
else
{
General.ShowErrorMessage(checkresult.Error, MessageBoxButtons.OK);
data.Resume();
General.WriteLogLine("Map saving failed: " + checkresult.Error);
return false;
}
} }
// Determine original map name // Determine original map name
@ -890,7 +897,7 @@ namespace CodeImp.DoomBuilder
try try
{ {
if(File.Exists(newfilepathname)) if(fileexists)
{ {
// mxd. Check if target wad already has a map with the same name // mxd. Check if target wad already has a map with the same name
if(purpose == SavePurpose.IntoFile) if(purpose == SavePurpose.IntoFile)
@ -925,7 +932,7 @@ namespace CodeImp.DoomBuilder
if((purpose != SavePurpose.IntoFile) && (newfilepathname != filepathname)) if((purpose != SavePurpose.IntoFile) && (newfilepathname != filepathname))
{ {
// Kill target file // Kill target file
if(File.Exists(newfilepathname)) File.Delete(newfilepathname); if(fileexists) File.Delete(newfilepathname);
// Kill .dbs settings file // Kill .dbs settings file
settingsfile = newfilepathname.Substring(0, newfilepathname.Length - 4) + ".dbs"; settingsfile = newfilepathname.Substring(0, newfilepathname.Length - 4) + ".dbs";
@ -940,7 +947,7 @@ namespace CodeImp.DoomBuilder
} }
// If the target file exists, we need to rebuild it // If the target file exists, we need to rebuild it
if(File.Exists(newfilepathname)) if(fileexists)
{ {
// Move the target file aside // Move the target file aside
origwadfile = newfilepathname + ".temp"; origwadfile = newfilepathname + ".temp";
@ -985,7 +992,7 @@ namespace CodeImp.DoomBuilder
if(!string.IsNullOrEmpty(origwadfile) && File.Exists(origwadfile)) if(!string.IsNullOrEmpty(origwadfile) && File.Exists(origwadfile))
{ {
//mxd. Clean-up //mxd. Clean-up
if(File.Exists(newfilepathname)) if(fileexists)
{ {
//mxd. We MAY've just deleted the map from the target file. Let's pretend this never happened //mxd. We MAY've just deleted the map from the target file. Let's pretend this never happened
if(targetwad != null) targetwad.Dispose(); if(targetwad != null) targetwad.Dispose();