diff --git a/src/ce_ddemangle.pas b/src/ce_ddemangle.pas index 59bf445e..8c2c3378 100644 --- a/src/ce_ddemangle.pas +++ b/src/ce_ddemangle.pas @@ -11,13 +11,11 @@ uses type TCEDDemangler = class - private + strict private fActive: boolean; - fDone: boolean; fProc: TCEProcess; fList, fOut: TStringList; - procedure procOutput(sender: TObject); - procedure init; + procedure procTerminate(sender: TObject); public constructor create; destructor destroy; override; @@ -38,9 +36,15 @@ var constructor TCEDDemangler.create; begin - init; fList := TStringList.Create; fOut := TStringList.Create; + fProc := TCEProcess.create(nil); + fProc.Executable:= exeFullName('ddemangle' + exeExt); + fProc.Options:= [poUsePipes]; + fProc.OnTerminate:=@procTerminate; + fProc.ShowWindow:= swoHIDE; + fProc.execute; + fActive := true; end; destructor TCEDDemangler.destroy; @@ -52,44 +56,28 @@ begin inherited; end; -procedure TCEDDemangler.init; +procedure TCEDDemangler.procTerminate(sender: TObject); begin - if assigned(fProc) and fProc.Running then - exit; - fProc.free; - fProc := TCEProcess.create(nil); - fProc.Executable:= exeFullName('ddemangle' + exeExt); - fProc.Options:= [poUsePipes]; - fProc.OnReadData:=@procOutput; - fProc.ShowWindow:= swoHIDE; - fProc.execute; - fActive := true; + fActive := false; end; procedure TCEDDemangler.demangle(const value: string); var - i: integer = 0; + nb: integer; begin - init; - fDone := false; if value.isNotEmpty then fProc.Input.Write(value[1], value.length); fProc.Input.WriteByte(10); - while not fDone do + while true do begin - Application.ProcessMessages; - i += 1; - if i = high(integer) then - i := 0; + nb := fProc.NumBytesAvailable; + if nb <> 0 then + break; end; -end; - -procedure TCEDDemangler.procOutput(sender: TObject); -begin + fProc.fillOutputStack; fProc.getFullLines(fOut); if fOut.Count <> 0 then fList.Add(fOut[0]); - fDone := true; end; function demangle(const value: string): string; diff --git a/src/ce_processes.pas b/src/ce_processes.pas index a260dcc9..77132eb3 100644 --- a/src/ce_processes.pas +++ b/src/ce_processes.pas @@ -34,6 +34,7 @@ type fOutputStack: TMemoryStream; fTerminateChecker: TTimer; fDoneTerminated: boolean; + fHasRead: boolean; procedure checkTerminated(sender: TObject); procedure setOnTerminate(value: TNotifyEvent); procedure setOnReadData(value: TNotifyEvent); @@ -53,6 +54,8 @@ type procedure getFullLines(list: TStrings; consume: boolean = true); // access to a flexible copy of TProcess.Output property OutputStack: TMemoryStream read fOutputStack; + // indicates if an output buffer is read + property hasRead: boolean read fHasRead; end; { @@ -111,6 +114,7 @@ end; procedure TCEProcess.Execute; begin + fHasRead := false; fOutputStack.Clear; fDoneTerminated := false; TAsyncProcess(self).OnReadData := @internalDoOnReadData; @@ -184,6 +188,7 @@ end; procedure TCEProcess.internalDoOnReadData(sender: TObject); begin + fHasRead := true; fillOutputStack; if fRealOnReadData <> nil then fRealOnReadData(self); @@ -191,6 +196,7 @@ end; procedure TCEProcess.internalDoOnTerminate(sender: TObject); begin + fHasRead := false; fTerminateChecker.Enabled := false; if fDoneTerminated then exit; fDoneTerminated := true;