1 /* ***** BEGIN LICENSE BLOCK *****
2 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
4 * The contents of this file are subject to the Mozilla Public License Version
5 * 1.1 (the "License"); you may not use this file except in compliance with
6 * the License. You may obtain a copy of the License at
7 * http://www.mozilla.org/MPL/
9 * Software distributed under the License is distributed on an "AS IS" basis,
10 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
11 * for the specific language governing rights and limitations under the
14 * The Original Code is Mozilla XULRunner.
16 * The Initial Developer of the Original Code is
17 * Benjamin Smedberg <benjamin@smedbergs.us>.
19 * Portions created by the Initial Developer are Copyright (C) 2005
20 * the Initial Developer. All Rights Reserved.
24 * Alternatively, the contents of this file may be used under the terms of
25 * either the GNU General Public License Version 2 or later (the "GPL"), or
26 * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
27 * in which case the provisions of the GPL or the LGPL are applicable instead
28 * of those above. If you wish to allow use of your version of this file only
29 * under the terms of either the GPL or the LGPL, and not to allow others to
30 * use your version of this file under the terms of the MPL, indicate your
31 * decision by deleting the provisions above and replace them with the notice
32 * and other provisions required by the GPL or the LGPL. If you do not delete
33 * the provisions above, a recipient may use your version of this file under
34 * the terms of any one of the MPL, the GPL or the LGPL.
36 * ***** END LICENSE BLOCK ***** */
38 #include "nsRegisterGRE.h"
39 #include "nsXPCOMGlue.h"
43 #include "nsILocalFile.h"
45 #include "nsAppRunner.h" // for MAXPATHLEN
46 #include "nsStringAPI.h"
47 #include "nsINIParser.h"
57 // If we can't register <buildid>.conf, we try to create a unique filename
58 // by looping through <buildid>_<int>.conf, but if something is seriously wrong
60 #define UNIQ_LOOP_LIMIT 1000
62 static const char kRegFileGlobal
[] = "global.reginfo";
63 static const char kRegFileUser
[] = "user.reginfo";
68 AutoFDClose(PRFileDesc
* fd
= nsnull
) : mFD(fd
) { }
69 ~AutoFDClose() { if (mFD
) PR_Close(mFD
); }
71 PRFileDesc
* operator= (PRFileDesc
*fd
) {
72 if (mFD
) PR_Close(mFD
);
77 operator PRFileDesc
* () { return mFD
; }
78 PRFileDesc
** operator &() { *this = nsnull
; return &mFD
; }
85 MakeConfFile(const char *regfile
, const nsCString
&greHome
,
86 const GREProperty
*aProperties
, PRUint32 aPropertiesLen
,
87 const char *aGREMilestone
)
89 // If the file exists, don't create it again!
90 if (access(regfile
, R_OK
) == 0)
95 { // scope "fd" so that we can delete the file if something goes wrong
96 AutoFDClose fd
= PR_Open(regfile
, PR_CREATE_FILE
| PR_WRONLY
| PR_TRUNCATE
,
101 static const char kHeader
[] =
102 "# Registration file generated by xulrunner. Do not edit.\n\n"
106 if (PR_fprintf(fd
, kHeader
, aGREMilestone
, greHome
.get()) <= 0)
109 for (PRUint32 i
= 0; i
< aPropertiesLen
; ++i
) {
110 if (PR_fprintf(fd
, "%s=%s\n",
111 aProperties
[i
].property
, aProperties
[i
].value
) <= 0)
124 RegisterXULRunner(PRBool aRegisterGlobally
, nsIFile
* aLocation
,
125 const GREProperty
*aProperties
, PRUint32 aPropertiesLen
,
126 const char *aGREMilestone
)
128 // Register ourself in /etc/gre.d or ~/.gre.d/ and record what key we created
129 // for future unregistration.
133 char root
[MAXPATHLEN
] = "/etc/gre.d";
135 if (!aRegisterGlobally
) {
136 char *home
= PR_GetEnv("HOME");
140 PR_snprintf(root
, MAXPATHLEN
, "%s/.gre.d", home
);
144 rv
= aLocation
->GetNativePath(greHome
);
148 nsCOMPtr
<nsIFile
> savedInfoFile
;
149 aLocation
->Clone(getter_AddRefs(savedInfoFile
));
150 nsCOMPtr
<nsILocalFile
> localSaved(do_QueryInterface(savedInfoFile
));
154 const char *infoname
= aRegisterGlobally
? kRegFileGlobal
: kRegFileUser
;
155 localSaved
->AppendNative(nsDependentCString(infoname
));
158 rv
= localSaved
->OpenNSPRFileDesc(PR_CREATE_FILE
| PR_RDWR
, 0664, &fd
);
163 char keyName
[MAXPATHLEN
];
165 PRInt32 r
= PR_Read(fd
, keyName
, MAXPATHLEN
);
169 char regfile
[MAXPATHLEN
];
174 PR_snprintf(regfile
, MAXPATHLEN
, "%s/%s.conf", root
, keyName
);
176 // There was already a .reginfo file, let's see if we are already
178 if (access(regfile
, R_OK
) == 0) {
179 fprintf(stderr
, "Warning: Configuration file '%s' already exists.\n"
180 "No action was performed.\n", regfile
);
184 rv
= localSaved
->OpenNSPRFileDesc(PR_CREATE_FILE
| PR_WRONLY
| PR_TRUNCATE
, 0664, &fd
);
189 if (access(root
, R_OK
| X_OK
) &&
191 fprintf(stderr
, "Error: could not create '%s'.\n",
196 PR_snprintf(regfile
, MAXPATHLEN
, "%s/%s.conf", root
, aGREMilestone
);
197 if (MakeConfFile(regfile
, greHome
, aProperties
, aPropertiesLen
,
199 PR_fprintf(fd
, "%s", aGREMilestone
);
203 for (int i
= 0; i
< UNIQ_LOOP_LIMIT
; ++i
) {
204 static char buildID
[30];
205 sprintf(buildID
, "%s_%i", aGREMilestone
, i
);
207 PR_snprintf(regfile
, MAXPATHLEN
, "%s/%s.conf", root
, buildID
);
209 if (MakeConfFile(regfile
, greHome
, aProperties
, aPropertiesLen
,
211 PR_Write(fd
, buildID
, strlen(buildID
));
220 UnregisterXULRunner(PRBool aRegisterGlobally
, nsIFile
* aLocation
,
221 const char *aGREMilestone
)
225 char root
[MAXPATHLEN
] = "/etc/gre.d";
227 if (!aRegisterGlobally
) {
228 char *home
= PR_GetEnv("HOME");
232 PR_snprintf(root
, MAXPATHLEN
, "%s/.gre.d", home
);
235 nsCOMPtr
<nsIFile
> savedInfoFile
;
236 aLocation
->Clone(getter_AddRefs(savedInfoFile
));
237 nsCOMPtr
<nsILocalFile
> localSaved (do_QueryInterface(savedInfoFile
));
241 const char *infoname
= aRegisterGlobally
? kRegFileGlobal
: kRegFileUser
;
242 localSaved
->AppendNative(nsDependentCString(infoname
));
244 PRFileDesc
* fd
= nsnull
;
245 rv
= localSaved
->OpenNSPRFileDesc(PR_RDONLY
, 0, &fd
);
251 char keyName
[MAXPATHLEN
];
252 PRInt32 r
= PR_Read(fd
, keyName
, MAXPATHLEN
);
255 localSaved
->Remove(PR_FALSE
);
262 char regFile
[MAXPATHLEN
];
263 PR_snprintf(regFile
, MAXPATHLEN
, "%s/%s.conf", root
, keyName
);
265 nsCOMPtr
<nsILocalFile
> lf
;
266 rv
= NS_NewNativeLocalFile(nsDependentCString(regFile
), PR_FALSE
,
276 rv
= p
.GetString(aGREMilestone
, "GRE_PATH", root
, MAXPATHLEN
);
280 rv
= NS_NewNativeLocalFile(nsDependentCString(root
), PR_TRUE
,
286 if (NS_SUCCEEDED(aLocation
->Equals(lf
, &eq
)) && eq
)