Mark msysGit as obsolete
[msysgit.git] / share / WinGit / install.iss
blob0f0514d7729228b2be3e9c5c02e48744a99aed7c
1 #define APP_NAME 'Git'
2 #define APP_VERSION '%APPVERSION%'
3 #define APP_URL 'http://code.google.com/p/msysgit/'
4 #define APP_BUILTINS 'etc\fileList-builtins.txt'
6 [Setup]
7 ; Compiler-related
8 InternalCompressLevel=max
9 OutputBaseFilename={#emit APP_NAME+'-'+APP_VERSION}
10 OutputDir=%OUTPUTDIR%
11 SolidCompression=yes
13 ; Installer-related
14 AllowNoIcons=yes
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}
22 DisableReadyPage=yes
23 InfoBeforeFile=gpl-2.0.rtf
24 PrivilegesRequired=none
25 UninstallDisplayIcon=etc\git.ico
27 ; Cosmetic
28 SetupIconFile=etc\git.ico
29 WizardSmallImageFile=git.bmp
31 [Tasks]
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
37 [Files]
38 Source: "*"; DestDir: "{app}"; Excludes: "\*.bmp, gpl-2.0.rtf, \install.*, \tmp.*, \bin\*install*"; Flags: recursesubdirs
39 Source: ReleaseNotes.rtf; DestDir: "{app}"; Flags: isreadme
41 [Icons]
42 Name: "{group}\Git GUI"; Filename: "{app}\bin\wish.exe"; Parameters: """{app}\bin\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
48 [Messages]
49 BeveledLabel={#emit APP_URL}
50 SetupAppTitle={#emit APP_NAME} Setup
51 SetupWindowTitle={#emit APP_NAME} Setup
53 [UninstallDelete]
54 Type: files; Name: "{app}\bin\git-*.exe"
55 Type: dirifempty; Name: "{app}\home\{username}"
56 Type: dirifempty; Name: "{app}\home"
58 [Code]
60 Helper methods
63 function GetShellFolder(Param:string):string;
64 begin
65 if IsAdminLoggedOn then begin
66 Param:='{common'+Param+'}';
67 end else begin
68 Param:='{user'+Param+'}';
69 end;
70 Result:=ExpandConstant(Param);
71 end;
73 function CreateHardLink(lpFileName,lpExistingFileName:string;lpSecurityAttributes:Integer):Boolean;
74 external 'CreateHardLinkA@Kernel32.dll';
76 function GetEnvStrings(VarName:string;AllUsers:Boolean):TArrayOfString;
77 var
78 Path:string;
79 i:Longint;
80 p:Integer;
81 begin
82 Path:='';
84 // See http://www.jrsoftware.org/isfaq.php#env
85 if AllUsers then begin
86 // We ignore errors here. The resulting array of strings will be empty.
87 RegQueryStringValue(HKEY_LOCAL_MACHINE,'SYSTEM\CurrentControlSet\Control\Session Manager\Environment',VarName,Path);
88 end else begin
89 // We ignore errors here. The resulting array of strings will be empty.
90 RegQueryStringValue(HKEY_CURRENT_USER,'Environment',VarName,Path);
91 end;
93 // Make sure we have at least one semicolon.
94 Path:=Path+';';
96 // Split the directories in PATH into an array of strings.
97 i:=0;
98 SetArrayLength(Result,0);
100 p:=Pos(';',Path);
101 while p>0 do begin
102 SetArrayLength(Result,i+1);
103 if p>1 then begin
104 Result[i]:=Copy(Path,1,p-1);
105 i:=i+1;
106 end;
107 Path:=Copy(Path,p+1,Length(Path));
108 p:=Pos(';',Path);
109 end;
110 end;
112 function SetEnvStrings(VarName:string;AllUsers,DeleteIfEmpty:Boolean;DirStrings:TArrayOfString):Boolean;
114 Path,KeyName:string;
115 i:Longint;
116 begin
117 // Merge all non-empty directory strings into a PATH variable.
118 Path:='';
119 for i:=0 to GetArrayLength(DirStrings)-1 do begin
120 if Length(DirStrings[i])>0 then begin
121 if Length(Path)>0 then begin
122 Path:=Path+';'+DirStrings[i];
123 end else begin
124 Path:=DirStrings[i];
125 end;
126 end;
127 end;
129 // See http://www.jrsoftware.org/isfaq.php#env
130 if AllUsers then begin
131 KeyName:='SYSTEM\CurrentControlSet\Control\Session Manager\Environment';
132 if DeleteIfEmpty and (Length(Path)=0) then begin
133 Result:=(not RegValueExists(HKEY_LOCAL_MACHINE,KeyName,VarName))
134 or RegDeleteValue(HKEY_LOCAL_MACHINE,KeyName,VarName);
135 end else begin
136 Result:=RegWriteStringValue(HKEY_LOCAL_MACHINE,KeyName,VarName,Path);
137 end;
138 end else begin
139 KeyName:='Environment';
140 if DeleteIfEmpty and (Length(Path)=0) then begin
141 Result:=(not RegValueExists(HKEY_CURRENT_USER,KeyName,VarName))
142 or RegDeleteValue(HKEY_CURRENT_USER,KeyName,VarName);
143 end else begin
144 Result:=RegWriteStringValue(HKEY_CURRENT_USER,KeyName,VarName,Path);
145 end;
146 end;
147 end;
149 const
150 PuTTYUninstallKey='SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\PuTTY_is1';
151 PuTTYPrivateKeyAssoc='PuTTYPrivateKey\shell\open\command';
153 function GetPuTTYLocation:string;
154 begin
155 if RegQueryStringValue(HKEY_LOCAL_MACHINE,PuTTYUninstallKey,'InstallLocation',Result) and DirExists(Result) then begin
156 // C:\Program Files\PuTTY\
157 Exit;
158 end;
159 if RegQueryStringValue(HKEY_CLASSES_ROOT,PuTTYPrivateKeyAssoc,'',Result) then begin
160 // "C:\Program Files\PuTTY\pageant.exe" "%1"
161 Result:=RemoveQuotes(Result);
162 // C:\Program Files\PuTTY\pageant.exe" "%1
163 Result:=ExtractFilePath(Result);
164 // C:\Program Files\PuTTY\
165 if DirExists(Result) then begin
166 Exit;
167 end;
168 end;
169 // Guess something.
170 Result:='C:\Program Files\PuTTY\';
171 end;
174 EnvPage,PuTTYPage:TWizardPage;
175 RdbGitBash,RdbGitCmd,RdbGitCmdTools:TRadioButton;
176 RdbOpenSSH,RdbPLink:TRadioButton;
177 EdtPLink:TEdit;
179 procedure BrowseForPuTTYFolder(Sender:TObject);
181 Path:string;
182 begin
183 Path:=ExtractFilePath(EdtPLink.Text);
184 BrowseForFolder('Please select the PuTTY folder:',Path,False);
185 Path:=Path+'\plink.exe';
186 if FileExists(Path) then begin
187 EdtPLink.Text:=Path;
188 RdbPLink.Checked:=True;
189 end else begin
190 MsgBox('Please enter a valid path to plink.exe.',mbError,MB_OK);
191 end;
192 end;
195 Installer code
198 procedure InitializeWizard;
200 LblGitBash,LblGitCmd,LblGitCmdTools,LblGitCmdToolsWarn:TLabel;
201 LblOpenSSH,LblPLink:TLabel;
202 BtnPLink:TButton;
203 begin
204 // Create a custom page for modifying the environment.
205 EnvPage:=CreateCustomPage(
206 wpSelectTasks,
207 'Adjusting your PATH environment',
208 'How would you like to use Git from the command line?'
211 // 1st choice
212 RdbGitBash:=TRadioButton.Create(EnvPage);
213 with RdbGitBash do begin
214 Parent:=EnvPage.Surface;
215 Caption:='Use Git Bash only';
216 Left:=ScaleX(4);
217 Top:=ScaleY(8);
218 Width:=ScaleX(129);
219 Height:=ScaleY(17);
220 Font.Style:=[fsBold];
221 TabOrder:=0;
222 Checked:=True;
223 end;
224 LblGitBash:=TLabel.Create(EnvPage);
225 with LblGitBash do begin
226 Parent:=EnvPage.Surface;
227 Caption:=
228 'This is the most conservative choice if you are concerned about the stability' + #13 +
229 'of your system. Your PATH will not be modified.';
230 Left:=ScaleX(28);
231 Top:=ScaleY(32);
232 Width:=ScaleX(405);
233 Height:=ScaleY(26);
234 end;
236 // 2nd choice
237 RdbGitCmd:=TRadioButton.Create(EnvPage);
238 with RdbGitCmd do begin
239 Parent:=EnvPage.Surface;
240 Caption:='Run Git from the Windows Command Prompt';
241 Left:=ScaleX(4);
242 Top:=ScaleY(76);
243 Width:=ScaleX(281);
244 Height:=ScaleY(17);
245 Font.Style:=[fsBold];
246 TabOrder:=1;
247 end;
248 LblGitCmd:=TLabel.Create(EnvPage);
249 with LblGitCmd do begin
250 Parent:=EnvPage.Surface;
251 Caption:=
252 'This option is considered safe and no conflicts with other tools are known.' + #13 +
253 'Only Git will be added to your PATH. Use this option if you want to use Git' + #13 +
254 'from a Cygwin Prompt (make sure to not have Cygwin''s Git installed).';
255 Left:=ScaleX(28);
256 Top:=ScaleY(100);
257 Width:=ScaleX(405);
258 Height:=ScaleY(39);
259 end;
261 // 3rd choice
262 RdbGitCmdTools:=TRadioButton.Create(EnvPage);
263 with RdbGitCmdTools do begin
264 Parent:=EnvPage.Surface;
265 Caption:='Run Git and included Unix tools from the Windows Command Prompt';
266 Left:=ScaleX(4);
267 Top:=ScaleY(152);
268 Width:=ScaleX(405);
269 Height:=ScaleY(17);
270 Font.Style:=[fsBold];
271 TabOrder:=2;
272 end;
273 LblGitCmdTools:=TLabel.Create(EnvPage);
274 with LblGitCmdTools do begin
275 Parent:=EnvPage.Surface;
276 Caption:='Both Git and its accompanying Unix tools will be added to your PATH.';
277 Left:=ScaleX(28);
278 Top:=ScaleY(176);
279 Width:=ScaleX(405);
280 Height:=ScaleY(13);
281 end;
282 LblGitCmdToolsWarn:=TLabel.Create(EnvPage);
283 with LblGitCmdToolsWarn do begin
284 Parent:=EnvPage.Surface;
285 Caption:=
286 'Warning: This will override Windows tools like find.exe and' + #13 +
287 'sort.exe. Select this option only if you understand the implications.';
288 Left:=ScaleX(28);
289 Top:=ScaleY(192);
290 Width:=ScaleX(376);
291 Height:=ScaleY(26);
292 Font.Color:=255;
293 Font.Style:=[fsBold];
294 end;
296 // Create a custom page for using PuTTY's plink instead of ssh.
297 PuTTYPage:=CreateCustomPage(
298 EnvPage.ID,
299 'Choosing the SSH executable',
300 'Which Secure Shell client program would you like Git to use?'
303 // 1st choice
304 RdbOpenSSH:=TRadioButton.Create(PuTTYPage);
305 with RdbOpenSSH do begin
306 Parent:=PuTTYPage.Surface;
307 Caption:='Use OpenSSH';
308 Left:=ScaleX(4);
309 Top:=ScaleY(8);
310 Width:=ScaleX(129);
311 Height:=ScaleY(17);
312 Font.Style:=[fsBold];
313 TabOrder:=0;
314 Checked:=True;
315 end;
316 LblOpenSSH:=TLabel.Create(PuTTYPage);
317 with LblOpenSSH do begin
318 Parent:=PuTTYPage.Surface;
319 Caption:=
320 'This uses ssh.exe that comes with Git. The GIT_SSH environment' + #13 +
321 'variable will not be modified.';
322 Left:=ScaleX(28);
323 Top:=ScaleY(32);
324 Width:=ScaleX(324);
325 Height:=ScaleY(26);
326 end;
328 // 2nd choice
329 RdbPLink:=TRadioButton.Create(PuTTYPage);
330 with RdbPLink do begin
331 Parent:=PuTTYPage.Surface;
332 Caption:='Use PLink';
333 Left:=ScaleX(4);
334 Top:=ScaleY(76);
335 Width:=ScaleX(281);
336 Height:=ScaleY(17);
337 Font.Style:=[fsBold];
338 TabOrder:=1;
339 end;
340 LblPLink:=TLabel.Create(PuTTYPage);
341 with LblPLink do begin
342 Parent:=PuTTYPage.Surface;
343 Caption:=
344 'This uses plink.exe from the PuTTY package which needs to be' + #13 +
345 'provided by the user. The GIT_SSH environment variable will be' + #13 +
346 'set to the path to plink.exe as specified below.';
347 Left:=ScaleX(28);
348 Top:=ScaleY(100);
349 Width:=ScaleX(316);
350 Height:=ScaleY(39);
351 end;
352 EdtPLink:=TEdit.Create(PuTTYPage);
353 with EdtPLink do begin
354 Parent:=PuTTYPage.Surface;
355 Text:=GetPuTTYLocation+'plink.exe';
356 if not FileExists(Text) then begin
357 Text:='';
358 end;
359 Left:=ScaleX(28);
360 Top:=ScaleY(148);
361 Width:=ScaleX(316);
362 Height:=ScaleY(13);
363 end;
364 BtnPLink:=TButton.Create(PuTTYPage);
365 with BtnPLink do begin
366 Parent:=PuTTYPage.Surface;
367 Caption:='...';
368 OnClick:=@BrowseForPuTTYFolder;
369 Left:=ScaleX(348);
370 Top:=ScaleY(148);
371 Width:=ScaleX(21);
372 Height:=ScaleY(21);
373 end;
374 end;
376 function NextButtonClick(CurPageID:Integer):Boolean;
377 begin
378 if CurPageID<>PuTTYPage.ID then begin
379 Result:=True;
380 Exit;
381 end;
383 Result:=RdbOpenSSH.Checked
384 or (RdbPLink.Checked and FileExists(EdtPLink.Text));
386 if not Result then begin
387 MsgBox('Please enter a valid path to plink.exe.',mbError,MB_OK);
388 end;
389 end;
391 procedure CurStepChanged(CurStep:TSetupStep);
393 AppDir,FileName,Cmd,Msg:string;
394 BuiltIns,EnvPath,EnvHome,EnvSSH:TArrayOfString;
395 Count,i:Longint;
396 IsNTFS:Boolean;
397 RootKey:Integer;
398 begin
399 if CurStep<>ssPostInstall then begin
400 Exit;
401 end;
403 AppDir:=ExpandConstant('{app}');
406 Create the built-ins
409 // Load the built-ins from a text file.
410 FileName:=ExpandConstant('{app}\'+'{#emit APP_BUILTINS}');
411 if LoadStringsFromFile(FileName,BuiltIns) then begin
412 // Check if we are running on NTFS.
413 IsNTFS:=False;
414 if SetNTFSCompression(AppDir+'\bin\git.exe',true) then begin
415 IsNTFS:=SetNTFSCompression(AppDir+'\bin\git.exe',false);
416 end;
418 Count:=GetArrayLength(BuiltIns)-1;
420 // Delete all scripts as they might have been replaced by built-ins by now.
421 for i:=0 to Count do begin
422 FileName:=ChangeFileExt(AppDir+'\'+BuiltIns[i],'');
423 if (FileExists(FileName) and (not DeleteFile(FileName))) then begin
424 Log('Line {#emit __LINE__}: Unable to delete script "'+FileName+'", ignoring.');
425 end;
426 end;
428 // Map the built-ins to git.exe.
429 if IsNTFS then begin
430 Log('Line {#emit __LINE__}: Partition seems to be NTFS, trying to create built-in aliases as hard links.');
432 for i:=0 to Count do begin
433 FileName:=AppDir+'\'+BuiltIns[i];
435 // On non-NTFS partitions, create hard links.
436 if (FileExists(FileName) and (not DeleteFile(FileName)))
437 or (not CreateHardLink(FileName,AppDir+'\bin\git.exe',0)) then begin
438 Log('Line {#emit __LINE__}: Unable to create hard link "'+FileName+'", will try to copy files.');
439 IsNTFS:=False;
440 Break;
441 end;
442 end;
444 Log('Line {#emit __LINE__}: Successfully created built-in aliases as hard links.');
445 end;
447 // The fallback is to copy the files.
448 if not IsNTFS then begin
449 Log('Line {#emit __LINE__}: Trying to create built-in aliases as file copies.');
451 for i:=0 to Count do begin
452 FileName:=AppDir+'\'+BuiltIns[i];
454 // On non-NTFS partitions, copy simply the files (overwriting existing ones).
455 if not FileCopy(AppDir+'\bin\git.exe',FileName,false) then begin
456 Msg:='Line {#emit __LINE__}: Unable to create file copy "'+FileName+'".';
457 MsgBox(Msg,mbError,MB_OK);
458 Log(Msg);
459 // This is not a critical error, Git could basically be used without the
460 // aliases for built-ins, so we continue.
461 end;
462 end;
464 Log('Line {#emit __LINE__}: Successfully created built-in aliases as file copies.');
465 end;
466 end else begin
467 Msg:='Line {#emit __LINE__}: Unable to read file "{#emit APP_BUILTINS}".';
468 MsgBox(Msg,mbError,MB_OK);
469 Log(Msg);
470 // This is not a critical error, Git could basically be used without the
471 // aliases for built-ins, so we continue.
472 end;
475 Modify the environment
477 This must happen no later than ssPostInstall to make
478 "ChangesEnvironment=yes" not happend before the change!
481 FileName:=AppDir+'\setup.ini';
483 // Delete GIT_SSH if a previous installation modified it.
484 EnvSSH:=GetEnvStrings('GIT_SSH',IsAdminLoggedOn);
485 if (GetArrayLength(EnvSSH)=1) and
486 (CompareStr(EnvSSH[0],GetIniString('Environment','GIT_SSH','',FileName))=0) then begin
487 if not SetEnvStrings('GIT_SSH',IsAdminLoggedOn,True,[]) then begin
488 Msg:='Line {#emit __LINE__}: Unable to reset GIT_SSH prior to install.';
489 MsgBox(Msg,mbError,MB_OK);
490 Log(Msg);
491 // This is not a critical error, the user can probably fix it manually,
492 // so we continue.
493 end;
494 end;
496 if RdbPLink.Checked then begin
497 SetArrayLength(EnvSSH,1);
498 EnvSSH[0]:=EdtPLink.Text;
499 if not SetEnvStrings('GIT_SSH',IsAdminLoggedOn,True,EnvSSH) then begin
500 Msg:='Line {#emit __LINE__}: Unable to set the GIT_SSH environment variable.';
501 MsgBox(Msg,mbError,MB_OK);
502 Log(Msg);
503 // This is not a critical error, the user can probably fix it manually,
504 // so we continue.
505 end;
507 // Mark that we have changed GIT_SSH.
508 if not SetIniString('Environment','GIT_SSH',EnvSSH[0],FileName) then begin
509 Msg:='Line {#emit __LINE__}: Unable to write to file "'+FileName+'".';
510 MsgBox(Msg,mbError,MB_OK);
511 Log(Msg);
512 // This is not a critical error, though uninstall / reinstall will probably not run cleanly,
513 // so we continue.
514 end;
515 end;
517 // Get the current user's directories in PATH.
518 EnvPath:=GetEnvStrings('PATH',IsAdminLoggedOn);
520 // First, remove the installation directory from PATH in any case.
521 for i:=0 to GetArrayLength(EnvPath)-1 do begin
522 if Pos(AppDir,EnvPath[i])=1 then begin
523 EnvPath[i]:='';
524 end;
525 end;
527 // Delete HOME if a previous installation modified it.
528 EnvHome:=GetEnvStrings('HOME',IsAdminLoggedOn);
529 if (GetArrayLength(EnvHome)=1) and
530 (CompareStr(EnvHome[0],GetIniString('Environment','HOME','',FileName))=0) then begin
531 if not SetEnvStrings('HOME',IsAdminLoggedOn,True,[]) then begin
532 Msg:='Line {#emit __LINE__}: Unable to reset HOME prior to install.';
533 MsgBox(Msg,mbError,MB_OK);
534 Log(Msg);
535 // This is not a critical error, the user can probably fix it manually,
536 // so we continue.
537 end;
538 end;
540 // Modify the PATH variable as requested by the user.
541 if RdbGitCmd.Checked or RdbGitCmdTools.Checked then begin
542 i:=GetArrayLength(EnvPath);
543 SetArrayLength(EnvPath,i+1);
545 // List \cmd before \bin so \cmd has higher priority and programs in
546 // there will be called in favor of those in \bin.
547 EnvPath[i]:=ExpandConstant('{app}\cmd');
549 if RdbGitCmdTools.Checked then begin
550 SetArrayLength(EnvPath,i+2);
551 EnvPath[i+1]:=ExpandConstant('{app}\bin');
553 // Set HOME for the Windows Command Prompt, but only if it has not been set manually before.
554 EnvHome:=GetEnvStrings('HOME',IsAdminLoggedOn);
555 i:=GetArrayLength(EnvHome);
556 if (i=0) or ((i=1) and (Length(EnvHome[0])=0)) then begin
557 SetArrayLength(EnvHome,1);
558 EnvHome[0]:=ExpandConstant('{%USERPROFILE}');
559 if not SetEnvStrings('HOME',IsAdminLoggedOn,True,EnvHome) then begin
560 Msg:='Line {#emit __LINE__}: Unable to set the HOME environment variable.';
561 MsgBox(Msg,mbError,MB_OK);
562 Log(Msg);
563 // This is not a critical error, the user can probably fix it manually,
564 // so we continue.
565 end;
567 // Mark that we have changed HOME.
568 if not SetIniString('Environment','HOME',EnvHome[0],FileName) then begin
569 Msg:='Line {#emit __LINE__}: Unable to write to file "'+FileName+'".';
570 MsgBox(Msg,mbError,MB_OK);
571 Log(Msg);
572 // This is not a critical error, though uninstall / reinstall will probably not run cleanly,
573 // so we continue.
574 end;
575 end;
576 end;
577 end;
579 // Set the current user's PATH directories.
580 if not SetEnvStrings('PATH',IsAdminLoggedOn,True,EnvPath) then begin
581 Msg:='Line {#emit __LINE__}: Unable to set the PATH environment variable.';
582 MsgBox(Msg,mbError,MB_OK);
583 Log(Msg);
584 // This is not a critical error, the user can probably fix it manually,
585 // so we continue.
586 end;
589 Create the Windows Explorer shell extensions
592 if IsAdminLoggedOn then begin
593 RootKey:=HKEY_LOCAL_MACHINE;
594 end else begin
595 RootKey:=HKEY_CURRENT_USER;
596 end;
598 if IsTaskSelected('shellextension') then begin
599 Cmd:=ExpandConstant('"{syswow64}\cmd.exe"');
600 if (not RegWriteStringValue(RootKey,'SOFTWARE\Classes\Directory\shell\git_shell','','Git Ba&sh Here'))
601 or (not RegWriteStringValue(RootKey,'SOFTWARE\Classes\Directory\shell\git_shell\command','',Cmd+' /c "pushd "%1" && "'+AppDir+'\bin\sh.exe" --login -i"')) then begin
602 Msg:='Line {#emit __LINE__}: Unable to create "Git Bash Here" shell extension.';
603 MsgBox(Msg,mbError,MB_OK);
604 Log(Msg);
605 // This is not a critical error, the user can probably fix it manually,
606 // so we continue.
607 end;
608 end;
610 if IsTaskSelected('guiextension') then begin
611 if (not RegWriteStringValue(RootKey,'SOFTWARE\Classes\Directory\shell\git_gui','','Git &GUI Here'))
612 or (not RegWriteStringValue(RootKey,'SOFTWARE\Classes\Directory\shell\git_gui\command','','"'+AppDir+'\bin\wish.exe" "'+AppDir+'\bin\git-gui" "--working-dir" "%1"')) then begin
613 Msg:='Line {#emit __LINE__}: Unable to create "Git GUI Here" shell extension.';
614 MsgBox(Msg,mbError,MB_OK);
615 Log(Msg);
616 // This is not a critical error, the user can probably fix it manually,
617 // so we continue.
618 end;
619 end;
620 end;
623 Uninstaller code
626 function InitializeUninstall:Boolean;
628 FileName,NewName,Msg:string;
629 begin
630 FileName:=ExpandConstant('{app}')+'\bin\ssh-agent.exe';
631 if FileExists(FileName) then begin
632 // Create a temporary copy of the file we try to delete.
633 NewName:=FileName+'.'+IntToStr(1000+Random(9000));
634 Result:=FileCopy(FileName,NewName,True) and DeleteFile(FileName);
636 if not Result then begin
637 Msg:='Line {#emit __LINE__}: Please stop all ssh-agent processes and run uninstall again.';
638 MsgBox(Msg,mbError,MB_OK);
639 Log(Msg);
641 // Clean-up the temporary copy (ignoring any errors).
642 DeleteFile(NewName);
643 end else begin
644 // Clean-up the temporary copy (ignoring any errors).
645 RenameFile(NewName,FileName);
646 end;
647 end else begin
648 Result:=True;
649 end;
650 end;
652 procedure CurUninstallStepChanged(CurUninstallStep:TUninstallStep);
654 AppDir,Command,Msg:string;
655 EnvPath,EnvHome,EnvSSH:TArrayOfString;
656 i:Longint;
657 RootKey:Integer;
658 begin
659 if CurUninstallStep<>usUninstall then begin
660 Exit;
661 end;
664 Modify the environment
666 This must happen no later than usUninstall to make
667 "ChangesEnvironment=yes" not happend before the change!
670 AppDir:=ExpandConstant('{app}');
671 Command:=AppDir+'\setup.ini';
673 // Reset the current user's GIT_SSH if we modified it.
674 EnvSSH:=GetEnvStrings('GIT_SSH',IsAdminLoggedOn);
675 if (GetArrayLength(EnvSSH)=1) and
676 (CompareStr(EnvSSH[0],GetIniString('Environment','GIT_SSH','',Command))=0) then begin
677 if not SetEnvStrings('GIT_SSH',IsAdminLoggedOn,True,[]) then begin
678 Msg:='Line {#emit __LINE__}: Unable to revert any possible changes to GIT_SSH.';
679 MsgBox(Msg,mbError,MB_OK);
680 Log(Msg);
681 // This is not a critical error, the user can probably fix it manually,
682 // so we continue.
683 end;
684 end;
686 // Get the current user's directories in PATH.
687 EnvPath:=GetEnvStrings('PATH',IsAdminLoggedOn);
689 // Remove the installation directory from PATH in any case, even if it
690 // was not added by the installer.
691 for i:=0 to GetArrayLength(EnvPath)-1 do begin
692 if Pos(AppDir,EnvPath[i])=1 then begin
693 EnvPath[i]:='';
694 end;
695 end;
697 // Reset the current user's directories in PATH.
698 if not SetEnvStrings('PATH',IsAdminLoggedOn,True,EnvPath) then begin
699 Msg:='Line {#emit __LINE__}: Unable to revert any possible changes to PATH.';
700 MsgBox(Msg,mbError,MB_OK);
701 Log(Msg);
702 // This is not a critical error, the user can probably fix it manually,
703 // so we continue.
704 end;
706 // Reset the current user's HOME if we modified it.
707 EnvHome:=GetEnvStrings('HOME',IsAdminLoggedOn);
708 if (GetArrayLength(EnvHome)=1) and
709 (CompareStr(EnvHome[0],GetIniString('Environment','HOME','',Command))=0) then begin
710 if not SetEnvStrings('HOME',IsAdminLoggedOn,True,[]) then begin
711 Msg:='Line {#emit __LINE__}: Unable to revert any possible changes to HOME.';
712 MsgBox(Msg,mbError,MB_OK);
713 Log(Msg);
714 // This is not a critical error, the user can probably fix it manually,
715 // so we continue.
716 end;
717 end;
719 if (FileExists(Command) and (not DeleteFile(Command))) then begin
720 Msg:='Line {#emit __LINE__}: Unable to delete file "'+Command+'".';
721 MsgBox(Msg,mbError,MB_OK);
722 Log(Msg);
723 // This is not a critical error, the user can probably fix it manually,
724 // so we continue.
725 end;
728 Delete the Windows Explorer shell extensions
731 if IsAdminLoggedOn then begin
732 RootKey:=HKEY_LOCAL_MACHINE;
733 end else begin
734 RootKey:=HKEY_CURRENT_USER;
735 end;
737 Command:='';
738 RegQueryStringValue(RootKey,'SOFTWARE\Classes\Directory\shell\git_shell\command','',Command);
739 if Pos(AppDir,Command)>0 then begin
740 if not RegDeleteKeyIncludingSubkeys(RootKey,'SOFTWARE\Classes\Directory\shell\git_shell') then begin
741 Msg:='Line {#emit __LINE__}: Unable to remove "Git Bash Here" shell extension.';
742 MsgBox(Msg,mbError,MB_OK);
743 Log(Msg);
744 // This is not a critical error, the user can probably fix it manually,
745 // so we continue.
746 end;
747 end;
749 Command:='';
750 RegQueryStringValue(RootKey,'SOFTWARE\Classes\Directory\shell\git_gui\command','',Command);
751 if Pos(AppDir,Command)>0 then begin
752 if not RegDeleteKeyIncludingSubkeys(RootKey,'SOFTWARE\Classes\Directory\shell\git_gui') then begin
753 Msg:='Line {#emit __LINE__}: Unable to remove "Git GUI Here" shell extension.';
754 MsgBox(Msg,mbError,MB_OK);
755 Log(Msg);
756 // This is not a critical error, the user can probably fix it manually,
757 // so we continue.
758 end;
759 end;
760 end;