2 #define APP_VERSION
'%APPVERSION%'
3 #define APP_URL
'http://code.google.com/p/msysgit/'
4 #define APP_BUILTINS
'etc\fileList-builtins.txt'
8 InternalCompressLevel
=max
9 OutputBaseFilename
={#emit APP_NAME+'-'+APP_VERSION}
15 AppName
={#emit APP_NAME}
16 AppPublisherURL
={#emit APP_URL}
17 AppVersion
={#emit APP_VERSION}
18 AppVerName
={#emit APP_NAME+' '+APP_VERSION}
19 ChangesEnvironment
=yes
20 DefaultDirName
={pf}\
{#emit APP_NAME}
21 DefaultGroupName
={#emit APP_NAME}
23 InfoBeforeFile
=gpl
-2.0.rtf
24 PrivilegesRequired
=none
25 UninstallDisplayIcon
=etc\git
.ico
28 SetupIconFile
=etc\git
.ico
29 WizardSmallImageFile
=git
.bmp
32 Name
: quicklaunchicon; Description
: "Create a &Quick Launch icon"; GroupDescription
: "Additional icons:"; Flags
: checkedonce
33 Name
: desktopicon; Description
: "Create a &Desktop icon"; GroupDescription
: "Additional icons:"; Flags
: checkedonce
34 Name
: shellextension
; Description
: "Add ""Git Ba&sh Here"""; GroupDescription
: "Windows Explorer integration:"; Flags
: checkedonce
35 Name
: guiextension
; Description
: "Add ""Git &GUI Here"""; GroupDescription
: "Windows Explorer integration:"; Flags
: checkedonce
38 Source
: "*"; DestDir
: "{app}"; Excludes
: "\*.bmp, gpl-2.0.rtf, \install.*, \tmp.*, \bin\*install*"; Flags
: recursesubdirs
39 Source
: ReleaseNotes
.rtf
; DestDir
: "{app}"; Flags
: isreadme
42 Name
: "{group}\Git GUI"; Filename
: "{app}\bin\wish.exe"; Parameters
: """{app}\libexec\git-core\git-gui"""; WorkingDir
: "%USERPROFILE%"; IconFilename
: "{app}\etc\git.ico"
43 Name
: "{group}\Git Bash"; Filename
: "{syswow64}\cmd.exe"; Parameters
: "/c """"{app}\bin\sh.exe"" --login -i"""; WorkingDir
: "%USERPROFILE%"; IconFilename
: "{app}\etc\git.ico"
44 Name
: "{group}\Uninstall Git"; Filename
: "{uninstallexe}"
45 Name
: "{userappdata}\Microsoft\Internet Explorer\Quick Launch\Git Bash"; Filename
: "{syswow64}\cmd.exe"; Parameters
: "/c """"{app}\bin\sh.exe"" --login -i"""; WorkingDir
: "%USERPROFILE%"; IconFilename
: "{app}\etc\git.ico"; Tasks
: quicklaunchicon
46 Name
: "{code:GetShellFolder|desktop}\Git Bash"; Filename
: "{syswow64}\cmd.exe"; Parameters
: "/c """"{app}\bin\sh.exe"" --login -i"""; WorkingDir
: "%USERPROFILE%"; IconFilename
: "{app}\etc\git.ico"; Tasks
: desktopicon
49 BeveledLabel
={#emit APP_URL}
50 SetupAppTitle
={#emit APP_NAME} Setup
51 SetupWindowTitle
={#emit APP_NAME} Setup
54 Type: files; Name
: "{app}\bin\git-*.exe"
55 Type: files; Name
: "{app}\libexec\git-core\git-*.exe"
56 Type: dirifempty; Name
: "{app}\home\{username}"
57 Type: dirifempty; Name
: "{app}\home"
64 function GetShellFolder(Param
:string):string;
66 if IsAdminLoggedOn
then begin
67 Param
:='{common'+Param
+'}';
69 Param
:='{user'+Param
+'}';
71 Result
:=ExpandConstant(Param
);
74 function CreateHardLink(lpFileName
,lpExistingFileName
:string;lpSecurityAttributes
:Integer):Boolean;
75 external 'CreateHardLinkA@Kernel32.dll';
77 function GetEnvStrings(VarName
:string;AllUsers
:Boolean):TArrayOfString
;
85 // See http
://www
.jrsoftware
.org
/isfaq
.php#env
86 if AllUsers
then begin
87 // We ignore errors here
. The resulting
array of strings will be empty
.
88 RegQueryStringValue(HKEY_LOCAL_MACHINE
,'SYSTEM\CurrentControlSet\Control\Session Manager\Environment',VarName
,Path
);
90 // We ignore errors here
. The resulting
array of strings will be empty
.
91 RegQueryStringValue(HKEY_CURRENT_USER
,'Environment',VarName
,Path
);
94 // Make sure we have at least one semicolon
.
97 // Split the directories
in PATH into an
array of strings
.
99 SetArrayLength(Result
,0);
103 SetArrayLength(Result
,i
+1);
105 Result
[i
]:=Copy(Path
,1,p
-1);
108 Path
:=Copy(Path
,p
+1,Length(Path
));
113 function SetEnvStrings(VarName
:string;AllUsers
,DeleteIfEmpty
:Boolean;DirStrings
:TArrayOfString
):Boolean;
118 // Merge all non
-empty directory strings into a PATH variable
.
120 for i
:=0 to GetArrayLength(DirStrings
)-1 do begin
121 if Length(DirStrings
[i
])>0 then begin
122 if Length(Path
)>0 then begin
123 Path
:=Path
+';'+DirStrings
[i
];
130 // See http
://www
.jrsoftware
.org
/isfaq
.php#env
131 if AllUsers
then begin
132 KeyName
:='SYSTEM\CurrentControlSet\Control\Session Manager\Environment';
133 if DeleteIfEmpty
and (Length(Path
)=0) then begin
134 Result
:=(not RegValueExists(HKEY_LOCAL_MACHINE
,KeyName
,VarName
))
135 or RegDeleteValue(HKEY_LOCAL_MACHINE
,KeyName
,VarName
);
137 Result
:=RegWriteStringValue(HKEY_LOCAL_MACHINE
,KeyName
,VarName
,Path
);
140 KeyName
:='Environment';
141 if DeleteIfEmpty
and (Length(Path
)=0) then begin
142 Result
:=(not RegValueExists(HKEY_CURRENT_USER
,KeyName
,VarName
))
143 or RegDeleteValue(HKEY_CURRENT_USER
,KeyName
,VarName
);
145 Result
:=RegWriteStringValue(HKEY_CURRENT_USER
,KeyName
,VarName
,Path
);
151 PuTTYUninstallKey
='SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\PuTTY_is1';
152 PuTTYPrivateKeyAssoc
='PuTTYPrivateKey\shell\open\command';
154 function GetPuTTYLocation
:string;
156 if RegQueryStringValue(HKEY_LOCAL_MACHINE
,PuTTYUninstallKey
,'InstallLocation',Result
) and DirExists(Result
) then begin
157 // C
:\
Program Files\PuTTY\
160 if RegQueryStringValue(HKEY_CLASSES_ROOT
,PuTTYPrivateKeyAssoc
,'',Result
) then begin
161 // "C:\Program Files\PuTTY\pageant.exe" "%1"
162 Result
:=RemoveQuotes(Result
);
163 // C
:\
Program Files\PuTTY\pageant
.exe
" "%1
164 Result
:=ExtractFilePath(Result
);
165 // C
:\
Program Files\PuTTY\
166 if DirExists(Result
) then begin
171 Result
:='C:\Program Files\PuTTY\';
187 GC_CRLFCommitAsIs = 3;
190 // Wizard page and variables for the Path options.
191 PathPage:TWizardPage;
192 RdbPath:array[GP_BashOnly..GP_CmdTools] of TRadioButton;
194 // Wizard page and variables for the SSH options.
195 PuTTYPage:TWizardPage;
196 RdbSSH:array[GS_OpenSSH..GS_PLink] of TRadioButton;
199 // Wizard page and variables for the CR/LF options.
200 CRLFPage:TWizardPage;
201 RdbCRLF:array[GC_LFOnly..GC_CRLFCommitAsIs] of TRadioButton;
203 procedure BrowseForPuTTYFolder(Sender:TObject);
207 Path:=ExtractFilePath(EdtPLink.Text);
208 BrowseForFolder('Please select the PuTTY folder
:',Path,False);
209 Path:=Path+'\plink
.exe
';
210 if FileExists(Path) then begin
212 RdbSSH[GS_PLink].Checked:=True;
214 MsgBox('Please enter a valid path
to plink
.exe
.',mbError,MB_OK);
222 procedure InitializeWizard;
224 LblGitBash,LblGitCmd,LblGitCmdTools,LblGitCmdToolsWarn:TLabel;
225 LblOpenSSH,LblPLink:TLabel;
226 LblLFOnly,LblCRLFAlways,LblCRLFCommitAsIs:TLabel;
230 // Create a custom page for modifying the environment.
231 PathPage:=CreateCustomPage(
233 'Adjusting your PATH environment
',
234 'How would you like
to use Git from the command line?
'
238 RdbPath[GP_BashOnly]:=TRadioButton.Create(PathPage);
239 with RdbPath[GP_BashOnly] do begin
240 Parent:=PathPage.Surface;
241 Caption:='Use Git Bash only
';
246 Font.Style:=[fsBold];
250 LblGitBash:=TLabel.Create(PathPage);
251 with LblGitBash do begin
252 Parent:=PathPage.Surface;
254 'This
is the most conservative choice
if you are concerned about the stability
' + #13 +
255 'of your
system. Your PATH will
not be modified
.';
263 RdbPath[GP_Cmd]:=TRadioButton.Create(PathPage);
264 with RdbPath[GP_Cmd] do begin
265 Parent:=PathPage.Surface;
266 Caption:='Run Git from the Windows Command Prompt
';
271 Font.Style:=[fsBold];
274 LblGitCmd:=TLabel.Create(PathPage);
275 with LblGitCmd do begin
276 Parent:=PathPage.Surface;
278 'This option
is considered safe
and no conflicts
with other tools are known
.' + #13 +
279 'Only Git will be added
to your PATH
. Use this option
if you want
to use Git
' + #13 +
280 'from a Cygwin
Prompt (make sure
to not have Cygwin
''s Git installed
).';
288 RdbPath[GP_CmdTools]:=TRadioButton.Create(PathPage);
289 with RdbPath[GP_CmdTools] do begin
290 Parent:=PathPage.Surface;
291 Caption:='Run Git
and included Unix tools from the Windows Command Prompt
';
296 Font.Style:=[fsBold];
299 LblGitCmdTools:=TLabel.Create(PathPage);
300 with LblGitCmdTools do begin
301 Parent:=PathPage.Surface;
302 Caption:='Both Git
and its accompanying Unix tools will be added
to your PATH
.';
308 LblGitCmdToolsWarn:=TLabel.Create(PathPage);
309 with LblGitCmdToolsWarn do begin
310 Parent:=PathPage.Surface;
312 'Warning
: This will
override Windows tools like find
.exe
and' + #13 +
313 'sort
.exe
. Select this option only
if you understand the implications
.';
319 Font.Style:=[fsBold];
322 // Restore the setting chosen during a previous install.
323 Data:=GetPreviousData('Path Option
','BashOnly
');
324 if Data='BashOnly
' then begin
325 RdbPath[GP_BashOnly].Checked:=True;
326 end else if Data='Cmd
' then begin
327 RdbPath[GP_Cmd].Checked:=True;
328 end else if Data='CmdTools
' then begin
329 RdbPath[GP_CmdTools].Checked:=True;
332 // Create a custom page for using PuTTY's plink instead
of ssh
.
333 PuTTYPage
:=CreateCustomPage(
335 'Choosing the SSH executable',
336 'Which Secure Shell client program would you like Git to use?'
340 RdbSSH
[GS_OpenSSH
]:=TRadioButton
.Create(PuTTYPage
);
341 with RdbSSH
[GS_OpenSSH
] do begin
342 Parent
:=PuTTYPage
.Surface
;
343 Caption
:='Use OpenSSH';
348 Font
.Style
:=[fsBold
];
352 LblOpenSSH
:=TLabel
.Create(PuTTYPage
);
353 with LblOpenSSH
do begin
354 Parent
:=PuTTYPage
.Surface
;
356 'This uses ssh.exe that comes with Git. The GIT_SSH environment' + #
13 +
357 'variable will not be modified.';
365 RdbSSH
[GS_PLink
]:=TRadioButton
.Create(PuTTYPage
);
366 with RdbSSH
[GS_PLink
] do begin
367 Parent
:=PuTTYPage
.Surface
;
368 Caption
:='Use PLink';
373 Font
.Style
:=[fsBold
];
376 LblPLink
:=TLabel
.Create(PuTTYPage
);
377 with LblPLink
do begin
378 Parent
:=PuTTYPage
.Surface
;
380 'This uses plink.exe from the PuTTY package which needs to be' + #
13 +
381 'provided by the user. The GIT_SSH environment variable will be' + #
13 +
382 'set to the path to plink.exe as specified below.';
388 EdtPLink
:=TEdit
.Create(PuTTYPage
);
389 with EdtPLink
do begin
390 Parent
:=PuTTYPage
.Surface
;
391 Text:=GetPuTTYLocation
+'plink.exe';
392 if not FileExists(Text) then begin
400 BtnPLink
:=TButton
.Create(PuTTYPage
);
401 with BtnPLink
do begin
402 Parent
:=PuTTYPage
.Surface
;
404 OnClick
:=@BrowseForPuTTYFolder
;
411 // Restore the setting chosen during a previous install
.
412 Data
:=GetPreviousData('SSH Option','OpenSSH');
413 if Data
='OpenSSH' then begin
414 RdbSSH
[GS_OpenSSH
].Checked
:=True;
415 end else if Data
='PLink' then begin
416 RdbSSH
[GS_PLink
].Checked
:=True;
419 // Create a custom page
for the autoCRLF setting
.
420 CRLFPage
:=CreateCustomPage(
422 'Choosing CR/LF behavior',
423 'Which CR/LF behavior would you like Git to have?'
427 RdbCRLF
[GC_LFOnly
]:=TRadioButton
.Create(CRLFPage
);
428 with RdbCRLF
[GC_LFOnly
] do begin
429 Parent
:=CRLFPage
.Surface
;
430 Caption
:='Use Unix style line endings';
435 Font
.Style
:=[fsBold
];
439 LblLFOnly
:=TLabel
.Create(CRLFPage
);
440 with LblLFOnly
do begin
441 Parent
:=CRLFPage
.Surface
;
443 'Choose this if a single Line Feed character ends your lines. Most Windows' + #
13 +
444 'programs can cope with these line endings. However, some editors, like' + #
13 +
445 'Notepad, will show everything in one line with this mode.';
453 RdbCRLF
[GC_CRLFAlways
]:=TRadioButton
.Create(CRLFPage
);
454 with RdbCRLF
[GC_CRLFAlways
] do begin
455 Parent
:=CRLFPage
.Surface
;
456 Caption
:='Use Windows style line endings';
461 Font
.Style
:=[fsBold
];
465 LblCRLFAlways
:=TLabel
.Create(CRLFPage
);
466 with LblCRLFAlways
do begin
467 Parent
:=CRLFPage
.Surface
;
469 'Choose this if your source code uses a Carriage Return and a Line Feed' + #
13 +
470 'character to end lines. This is the DOS convention; your checked-out files' + #
13 +
471 'might not be handled gracefully by MSYS / Cygwin command line utilities.';
479 RdbCRLF
[GC_CRLFCommitAsIs
]:=TRadioButton
.Create(CRLFPage
);
480 with RdbCRLF
[GC_CRLFCommitAsIs
] do begin
481 Parent
:=CRLFPage
.Surface
;
482 Caption
:='Commit line endings as they are';
487 Font
.Style
:=[fsBold
];
491 LblCRLFCommitAsIs
:=TLabel
.Create(CRLFPage
);
492 with LblCRLFCommitAsIs
do begin
493 Parent
:=CRLFPage
.Surface
;
495 'Choose this if you know what you are doing and want to track the files with' + #
13 +
496 'the line endings exactly as they appear in the files. This option might' + #
13 +
497 'cause your projects to be hard to use on other platforms.';
504 // Restore the setting chosen during a previous install
.
505 Data
:=GetPreviousData('CRLF Option','CRLFAlways');
506 if Data
='LFOnly' then begin
507 RdbCRLF
[GC_LFOnly
].Checked
:=True;
508 end else if Data
='CRLFAlways' then begin
509 RdbCRLF
[GC_CRLFAlways
].Checked
:=True;
510 end else if Data
='CRLFCommitAsIs' then begin
511 RdbCRLF
[GC_CRLFCommitAsIs
].Checked
:=True;
515 function NextButtonClick(CurPageID
:Integer):Boolean;
517 if CurPageID
<>PuTTYPage
.ID
then begin
522 Result
:=RdbSSH
[GS_OpenSSH
].Checked
523 or (RdbSSH
[GS_PLink
].Checked
and FileExists(EdtPLink
.Text));
525 if not Result
then begin
526 MsgBox('Please enter a valid path to plink.exe.',mbError
,MB_OK
);
530 procedure CurStepChanged(CurStep
:TSetupStep
);
532 AppDir
,FileName
,Cmd
,Msg
:string;
533 BuiltIns
,EnvPath
,EnvHome
,EnvSSH
:TArrayOfString
;
539 if CurStep
<>ssPostInstall
then begin
543 AppDir
:=ExpandConstant('{app}');
549 // Load the built
-ins from a
text file.
550 FileName
:=ExpandConstant('{app}\'+'{#emit APP_BUILTINS}');
551 if LoadStringsFromFile(FileName,BuiltIns) then begin
552 // Check if we are running on NTFS.
554 if SetNTFSCompression(AppDir+'\bin\git
.exe
',true) then begin
555 IsNTFS:=SetNTFSCompression(AppDir+'\bin\git
.exe
',false);
558 Count:=GetArrayLength(BuiltIns)-1;
560 // Delete all scripts as they might have been replaced by built-ins by now.
561 for i:=0 to Count do begin
562 FileName:=ChangeFileExt(AppDir+'\'+BuiltIns
[i
],'');
563 if (FileExists(FileName
) and (not DeleteFile(FileName
))) then begin
564 Log('Line {#emit __LINE__}: Unable to delete script "'+FileName
+'", ignoring.');
568 // Map the built
-ins
to git
.exe
.
570 Log('Line {#emit __LINE__}: Partition seems to be NTFS, trying to create built-in aliases as hard links.');
572 for i
:=0 to Count
do begin
573 FileName
:=AppDir
+'\'+BuiltIns[i];
575 // On non-NTFS partitions, create hard links.
576 if (FileExists(FileName) and (not DeleteFile(FileName)))
577 or (not CreateHardLink(FileName,AppDir+'\bin\git
.exe
',0)) then begin
578 Log('Line
{#emit __LINE__}: Unable
to create hard link
"'+FileName+'", will
try to copy
files.');
584 Log('Line
{#emit __LINE__}: Successfully created built
-in aliases
as hard links
.');
587 // The fallback is to copy the files.
588 if not IsNTFS then begin
589 Log('Line
{#emit __LINE__}: Trying
to create built
-in aliases
as file copies
.');
591 for i:=0 to Count do begin
592 FileName:=AppDir+'\'+BuiltIns
[i
];
594 // On non
-NTFS partitions
, copy simply the
files (overwriting existing ones
).
595 if not FileCopy(AppDir
+'\bin\git.exe',FileName
,false) then begin
596 Msg
:='Line {#emit __LINE__}: Unable to create file copy "'+FileName
+'".';
597 MsgBox(Msg
,mbError
,MB_OK
);
599 // This
is not a critical error
, Git could basically be used without the
600 // aliases
for built
-ins
, so we continue
.
604 Log('Line {#emit __LINE__}: Successfully created built-in aliases as file copies.');
607 // Delete any duplicate
files in case we are updating from a non
-libexec
to a libexec directory layout
.
608 if FindFirst(AppDir
+'\libexec\git-core\*',FindRec
) then begin
610 if (FindRec
.Attributes
and FILE_ATTRIBUTE_DIRECTORY
)=0 then begin
611 FileName
:=AppDir
+'\bin\'+FindRec.name;
612 if (FileExists(FileName) and (not DeleteFile(FileName))) then begin
613 Log('Line
{#emit __LINE__}: Unable
to delete dupe
"'+FileName+'", ignoring
.');
616 until not FindNext(FindRec);
620 Msg:='Line
{#emit __LINE__}: Unable
to read file "{#emit APP_BUILTINS}".';
621 MsgBox(Msg,mbError,MB_OK);
623 // This is not a critical error, Git could basically be used without the
624 // aliases for built-ins, so we continue.
631 if RdbCRLF[GC_LFOnly].checked then begin
632 Cmd:='core
.autoCRLF input
';
633 end else if RdbCRLF[GC_CRLFAlways].checked then begin
634 Cmd:='core
.autoCRLF
true';
636 Cmd:='core
.autoCRLF
false';
638 if not Exec(AppDir + '\bin\git
-config
.exe
', '-f gitconfig
' + Cmd,
639 AppDir + '\etc
', SW_HIDE, ewWaitUntilTerminated, i) then begin
640 Msg:='Could
not set CR
/LF behavior
: ' + Cmd;
641 MsgBox(Msg,mbError,MB_OK);
646 Modify the environment
648 This must happen no later than ssPostInstall to make
649 "ChangesEnvironment=yes" not happend before the change!
652 FileName:=AppDir+'\setup
.ini
';
654 // Delete GIT_SSH if a previous installation modified it.
655 EnvSSH:=GetEnvStrings('GIT_SSH
',IsAdminLoggedOn);
656 if (GetArrayLength(EnvSSH)=1) and
657 (CompareStr(EnvSSH[0],GetIniString('Environment
','GIT_SSH
','',FileName))=0) then begin
658 if not SetEnvStrings('GIT_SSH
',IsAdminLoggedOn,True,[]) then begin
659 Msg:='Line
{#emit __LINE__}: Unable
to reset GIT_SSH prior
to install
.';
660 MsgBox(Msg,mbError,MB_OK);
662 // This is not a critical error, the user can probably fix it manually,
667 if RdbSSH[GS_PLink].Checked then begin
668 SetArrayLength(EnvSSH,1);
669 EnvSSH[0]:=EdtPLink.Text;
670 if not SetEnvStrings('GIT_SSH
',IsAdminLoggedOn,True,EnvSSH) then begin
671 Msg:='Line
{#emit __LINE__}: Unable
to set the GIT_SSH environment variable
.';
672 MsgBox(Msg,mbError,MB_OK);
674 // This is not a critical error, the user can probably fix it manually,
678 // Mark that we have changed GIT_SSH.
679 if not SetIniString('Environment
','GIT_SSH
',EnvSSH[0],FileName) then begin
680 Msg:='Line
{#emit __LINE__}: Unable
to write
to file "'+FileName+'".';
681 MsgBox(Msg,mbError,MB_OK);
683 // This is not a critical error, though uninstall / reinstall will probably not run cleanly,
688 // Get the current user's directories
in PATH
.
689 EnvPath
:=GetEnvStrings('PATH',IsAdminLoggedOn
);
691 // First
, remove the installation directory from PATH
in any
case.
692 for i
:=0 to GetArrayLength(EnvPath
)-1 do begin
693 if Pos(AppDir
,EnvPath
[i
])=1 then begin
698 // Delete HOME
if a previous installation modified it
.
699 EnvHome
:=GetEnvStrings('HOME',IsAdminLoggedOn
);
700 if (GetArrayLength(EnvHome
)=1) and
701 (CompareStr(EnvHome
[0],GetIniString('Environment','HOME','',FileName
))=0) then begin
702 if not SetEnvStrings('HOME',IsAdminLoggedOn
,True,[]) then begin
703 Msg
:='Line {#emit __LINE__}: Unable to reset HOME prior to install.';
704 MsgBox(Msg
,mbError
,MB_OK
);
706 // This
is not a critical error
, the user can probably fix it manually
,
711 // Modify the PATH variable
as requested by the user
.
712 if RdbPath
[GP_Cmd
].Checked
or RdbPath
[GP_CmdTools
].Checked
then begin
713 i
:=GetArrayLength(EnvPath
);
714 SetArrayLength(EnvPath
,i
+1);
716 // List \cmd before
\bin so \cmd has higher priority
and programs
in
717 // there will be called
in favor
of those
in \bin
.
718 EnvPath
[i
]:=ExpandConstant('{app}\cmd');
720 if RdbPath
[GP_CmdTools
].Checked
then begin
721 SetArrayLength(EnvPath
,i
+3);
722 EnvPath
[i
+1]:=ExpandConstant('{app}\bin');
723 EnvPath
[i
+2]:=ExpandConstant('{app}\libexec\git-core');
725 // Set HOME
for the Windows Command Prompt
, but only
if it has
not been
set manually before
.
726 EnvHome
:=GetEnvStrings('HOME',IsAdminLoggedOn
);
727 i
:=GetArrayLength(EnvHome
);
728 if (i
=0) or ((i
=1) and (Length(EnvHome
[0])=0)) then begin
729 SetArrayLength(EnvHome
,1);
730 EnvHome
[0]:=ExpandConstant('{%USERPROFILE}');
731 if not SetEnvStrings('HOME',IsAdminLoggedOn
,True,EnvHome
) then begin
732 Msg
:='Line {#emit __LINE__}: Unable to set the HOME environment variable.';
733 MsgBox(Msg
,mbError
,MB_OK
);
735 // This
is not a critical error
, the user can probably fix it manually
,
739 // Mark that we have changed HOME
.
740 if not SetIniString('Environment','HOME',EnvHome
[0],FileName
) then begin
741 Msg
:='Line {#emit __LINE__}: Unable to write to file "'+FileName
+'".';
742 MsgBox(Msg
,mbError
,MB_OK
);
744 // This
is not a critical error
, though uninstall
/ reinstall will probably
not run cleanly
,
751 // Set the current user
's PATH directories.
752 if not SetEnvStrings('PATH
',IsAdminLoggedOn,True,EnvPath) then begin
753 Msg:='Line
{#emit __LINE__}: Unable
to set the PATH environment variable
.';
754 MsgBox(Msg,mbError,MB_OK);
756 // This is not a critical error, the user can probably fix it manually,
761 Create the Windows Explorer shell extensions
764 if IsAdminLoggedOn then begin
765 RootKey:=HKEY_LOCAL_MACHINE;
767 RootKey:=HKEY_CURRENT_USER;
770 if IsTaskSelected('shellextension
') then begin
771 Cmd:=ExpandConstant('"{syswow64}\cmd.exe"');
772 if (not RegWriteStringValue(RootKey,'SOFTWARE\Classes\Directory\shell\git_shell
','','Git Ba
&sh Here
'))
773 or (not RegWriteStringValue(RootKey,'SOFTWARE\Classes\Directory\shell\git_shell\command
','',Cmd+' /c
"pushd "%1" && "'+AppDir+'\bin\sh
.exe
" --login -i"')) then begin
774 Msg:='Line
{#emit __LINE__}: Unable
to create
"Git Bash Here" shell extension
.';
775 MsgBox(Msg,mbError,MB_OK);
777 // This is not a critical error, the user can probably fix it manually,
782 if IsTaskSelected('guiextension
') then begin
783 if (not RegWriteStringValue(RootKey,'SOFTWARE\Classes\Directory\shell\git_gui
','','Git
&GUI Here
'))
784 or (not RegWriteStringValue(RootKey,'SOFTWARE\Classes\Directory\shell\git_gui\command
','','"'+AppDir+'\bin\wish.exe" "'+AppDir+'\libexec\git-core\git-gui" "--working-dir" "%1"')) then begin
785 Msg:='Line
{#emit __LINE__}: Unable
to create
"Git GUI Here" shell extension
.';
786 MsgBox(Msg,mbError,MB_OK);
788 // This is not a critical error, the user can probably fix it manually,
794 procedure RegisterPreviousData(PreviousDataKey:Integer);
800 if RdbPath[GP_BashOnly].Checked then begin
802 end else if RdbPath[GP_Cmd].Checked then begin
804 end else if RdbPath[GP_CmdTools].Checked then begin
807 SetPreviousData(PreviousDataKey,'Path Option
',Data);
811 if RdbSSH[GS_OpenSSH].Checked then begin
813 end else if RdbSSH[GS_PLink].Checked then begin
816 SetPreviousData(PreviousDataKey,'SSH Option
',Data);
818 // Git CR/LF options.
820 if RdbCRLF[GC_LFOnly].Checked then begin
822 end else if RdbCRLF[GC_CRLFAlways].Checked then begin
824 end else if RdbCRLF[GC_CRLFCommitAsIs].Checked then begin
825 Data:='CRLFCommitAsIs
';
827 SetPreviousData(PreviousDataKey,'CRLF Option
',Data);
834 function InitializeUninstall:Boolean;
836 FileName,NewName,Msg:string;
838 FileName:=ExpandConstant('{app}')+'\bin\ssh
-agent
.exe
';
839 if FileExists(FileName) then begin
840 // Create a temporary copy of the file we try to delete.
841 NewName:=FileName+'.'+IntToStr(1000+Random(9000));
842 Result:=FileCopy(FileName,NewName,True) and DeleteFile(FileName);
844 if not Result then begin
845 Msg:='Line
{#emit __LINE__}: Please stop all ssh
-agent processes
and run uninstall again
.';
846 MsgBox(Msg,mbError,MB_OK);
849 // Clean-up the temporary copy (ignoring any errors).
852 // Clean-up the temporary copy (ignoring any errors).
853 RenameFile(NewName,FileName);
860 procedure CurUninstallStepChanged(CurUninstallStep:TUninstallStep);
862 AppDir,Command,Msg:string;
863 EnvPath,EnvHome,EnvSSH:TArrayOfString;
867 if CurUninstallStep<>usUninstall then begin
872 Modify the environment
874 This must happen no later than usUninstall to make
875 "ChangesEnvironment=yes" not happend before the change!
878 AppDir:=ExpandConstant('{app}');
879 Command:=AppDir+'\setup
.ini
';
881 // Reset the current user's GIT_SSH
if we modified it
.
882 EnvSSH
:=GetEnvStrings('GIT_SSH',IsAdminLoggedOn
);
883 if (GetArrayLength(EnvSSH
)=1) and
884 (CompareStr(EnvSSH
[0],GetIniString('Environment','GIT_SSH','',Command
))=0) then begin
885 if not SetEnvStrings('GIT_SSH',IsAdminLoggedOn
,True,[]) then begin
886 Msg
:='Line {#emit __LINE__}: Unable to revert any possible changes to GIT_SSH.';
887 MsgBox(Msg
,mbError
,MB_OK
);
889 // This
is not a critical error
, the user can probably fix it manually
,
894 // Get the current user
's directories in PATH.
895 EnvPath:=GetEnvStrings('PATH
',IsAdminLoggedOn);
897 // Remove the installation directory from PATH in any case, even if it
898 // was not added by the installer.
899 for i:=0 to GetArrayLength(EnvPath)-1 do begin
900 if Pos(AppDir,EnvPath[i])=1 then begin
905 // Reset the current user's directories
in PATH
.
906 if not SetEnvStrings('PATH',IsAdminLoggedOn
,True,EnvPath
) then begin
907 Msg
:='Line {#emit __LINE__}: Unable to revert any possible changes to PATH.';
908 MsgBox(Msg
,mbError
,MB_OK
);
910 // This
is not a critical error
, the user can probably fix it manually
,
914 // Reset the current user
's HOME if we modified it.
915 EnvHome:=GetEnvStrings('HOME
',IsAdminLoggedOn);
916 if (GetArrayLength(EnvHome)=1) and
917 (CompareStr(EnvHome[0],GetIniString('Environment
','HOME
','',Command))=0) then begin
918 if not SetEnvStrings('HOME
',IsAdminLoggedOn,True,[]) then begin
919 Msg:='Line
{#emit __LINE__}: Unable
to revert any possible changes
to HOME
.';
920 MsgBox(Msg,mbError,MB_OK);
922 // This is not a critical error, the user can probably fix it manually,
927 if (FileExists(Command) and (not DeleteFile(Command))) then begin
928 Msg:='Line
{#emit __LINE__}: Unable
to delete
file "'+Command+'".';
929 MsgBox(Msg,mbError,MB_OK);
931 // This is not a critical error, the user can probably fix it manually,
936 Delete the Windows Explorer shell extensions
939 if IsAdminLoggedOn then begin
940 RootKey:=HKEY_LOCAL_MACHINE;
942 RootKey:=HKEY_CURRENT_USER;
946 RegQueryStringValue(RootKey,'SOFTWARE\Classes\Directory\shell\git_shell\command
','',Command);
947 if Pos(AppDir,Command)>0 then begin
948 if not RegDeleteKeyIncludingSubkeys(RootKey,'SOFTWARE\Classes\Directory\shell\git_shell
') then begin
949 Msg:='Line
{#emit __LINE__}: Unable
to remove
"Git Bash Here" shell extension
.';
950 MsgBox(Msg,mbError,MB_OK);
952 // This is not a critical error, the user can probably fix it manually,
958 RegQueryStringValue(RootKey,'SOFTWARE\Classes\Directory\shell\git_gui\command
','',Command);
959 if Pos(AppDir,Command)>0 then begin
960 if not RegDeleteKeyIncludingSubkeys(RootKey,'SOFTWARE\Classes\Directory\shell\git_gui
') then begin
961 Msg:='Line
{#emit __LINE__}: Unable
to remove
"Git GUI Here" shell extension
.';
962 MsgBox(Msg,mbError,MB_OK);
964 // This is not a critical error, the user can probably fix it manually,