Installer: Early check whether the installation directory is writable
[msysgit.git] / share / WinGit / helpers.inc.iss
blob769818f16db9d7d0a69bdeeb351e35b6384aee8c
1 // Copies a NULL-terminated array of characters to a string.
2 function ArrayToString(Chars:array of Char):String;
3 var
4 Len,i:Longint;
5 begin
6 Len:=GetArrayLength(Chars);
7 SetLength(Result,Len);
9 i:=0;
10 while (i<Len) and (Chars[i]<>#0) do begin
11 Result[i+1]:=Chars[i];
12 Inc(i);
13 end;
15 SetLength(Result,i);
16 end;
18 // Copies a string to a NULL-terminated array of characters.
19 function StringToArray(Str:String):array of Char;
20 var
21 Len,i:Longint;
22 begin
23 Len:=Length(Str);
24 SetArrayLength(Result,Len+1);
26 i:=0;
27 while i<Len do begin
28 Result[i]:=Str[i+1];
29 Inc(i);
30 end;
32 Result[i]:=#0;
33 end;
35 // Returns the path to the common or user shell folder as specified in "Param".
36 function GetShellFolder(Param:string):string;
37 begin
38 if IsAdminLoggedOn then begin
39 Param:='{common'+Param+'}';
40 end else begin
41 Param:='{user'+Param+'}';
42 end;
43 Result:=ExpandConstant(Param);
44 end;
46 // Returns the value(s) of the environment variable "VarName", which is tokenized
47 // by ";" into an array of strings. This makes it easy query PATH-like variables
48 // in addition to normal variables. If "AllUsers" is true, the common variables
49 // are searched, else the user-specific ones.
50 function GetEnvStrings(VarName:string;AllUsers:Boolean):TArrayOfString;
51 var
52 Path:string;
53 i:Longint;
54 p:Integer;
55 begin
56 Path:='';
58 // See http://www.jrsoftware.org/isfaq.php#env
59 if AllUsers then begin
60 // We ignore errors here. The resulting array of strings will be empty.
61 RegQueryStringValue(HKEY_LOCAL_MACHINE,'SYSTEM\CurrentControlSet\Control\Session Manager\Environment',VarName,Path);
62 end else begin
63 // We ignore errors here. The resulting array of strings will be empty.
64 RegQueryStringValue(HKEY_CURRENT_USER,'Environment',VarName,Path);
65 end;
67 // Make sure we have at least one semicolon.
68 Path:=Path+';';
70 // Split the directories in PATH into an array of strings.
71 i:=0;
72 SetArrayLength(Result,0);
74 p:=Pos(';',Path);
75 while p>0 do begin
76 SetArrayLength(Result,i+1);
77 if p>1 then begin
78 Result[i]:=Copy(Path,1,p-1);
79 i:=i+1;
80 end;
81 Path:=Copy(Path,p+1,Length(Path));
82 p:=Pos(';',Path);
83 end;
84 end;
86 // Sets the environment variable "VarName" to the concatenation of "DirStrings"
87 // using ";" as the delimiter. If "AllUsers" is true, a common variable is set,
88 // else a user-specific one. If "DeleteIfEmpty" is true and "DirStrings" is
89 // empty, "VarName" is deleted instead of set if it exists.
90 function SetEnvStrings(VarName:string;AllUsers,DeleteIfEmpty:Boolean;DirStrings:TArrayOfString):Boolean;
91 var
92 Path,KeyName:string;
93 i:Longint;
94 begin
95 // Merge all non-empty directory strings into a PATH variable.
96 Path:='';
97 for i:=0 to GetArrayLength(DirStrings)-1 do begin
98 if Length(DirStrings[i])>0 then begin
99 if Length(Path)>0 then begin
100 Path:=Path+';'+DirStrings[i];
101 end else begin
102 Path:=DirStrings[i];
103 end;
104 end;
105 end;
107 // See http://www.jrsoftware.org/isfaq.php#env
108 if AllUsers then begin
109 KeyName:='SYSTEM\CurrentControlSet\Control\Session Manager\Environment';
110 if DeleteIfEmpty and (Length(Path)=0) then begin
111 Result:=(not RegValueExists(HKEY_LOCAL_MACHINE,KeyName,VarName)) or
112 RegDeleteValue(HKEY_LOCAL_MACHINE,KeyName,VarName);
113 end else begin
114 Result:=RegWriteStringValue(HKEY_LOCAL_MACHINE,KeyName,VarName,Path);
115 end;
116 end else begin
117 KeyName:='Environment';
118 if DeleteIfEmpty and (Length(Path)=0) then begin
119 Result:=(not RegValueExists(HKEY_CURRENT_USER,KeyName,VarName)) or
120 RegDeleteValue(HKEY_CURRENT_USER,KeyName,VarName);
121 end else begin
122 Result:=RegWriteStringValue(HKEY_CURRENT_USER,KeyName,VarName,Path);
123 end;
124 end;
125 end;
127 // As IsComponentSelected() is not supported during uninstall, this work-around
128 // simply checks the Registry. This is unreliable if the user runs the installer
129 // twice, the first time selecting the component, the second deselecting it.
130 function IsComponentInstalled(Component:String):Boolean;
132 UninstallKey,UninstallValue:String;
133 Value:String;
134 begin
135 Result:=False;
137 UninstallKey:='SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\{#APP_NAME}_is1';
138 UninstallValue:='Inno Setup: Selected Components';
140 if RegQueryStringValue(HKEY_LOCAL_MACHINE,UninstallKey,UninstallValue,Value) then begin
141 Result:=(Pos(Component,Value)>0);
142 end;
143 end;
145 // Checks whether the specified directory can be created and written to.
146 // Note that the created dummy file is not explicitly deleted here, so that
147 // needs to be done as part of the uninstall process.
148 function IsDirWritable(DirName:String):Boolean;
150 FileName:String;
151 begin
152 Result:=False;
154 if not ForceDirectories(DirName) then begin
155 Exit;
156 end;
158 FileName:=DirName+'\setup.ini';
160 if not SetIniBool('Dummy','Writable',true,FileName) then begin
161 Exit;
162 end;
164 Result:=GetIniBool('Dummy','Writable',false,FileName);
165 end;