Update contrib.
1 // Copyright (c) 1998-2009 Nokia Corporation and/or its subsidiary(-ies).
2 // All rights reserved.
3 // This component and the accompanying materials are made available
4 // under the terms of "Eclipse Public License v1.0"
5 // which accompanies this distribution, and is available
6 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
8 // Initial Contributors:
9 // Nokia Corporation - initial contribution.
14 // Common code useful to all crt0 variants. This is kept in the DLL to allow us to
15 // change it in future releases.
23 #include <unistd.h> // for chdir
24 #include <stdlib.h> // for calloc
25 #include <string.h> // for strdup
27 const TInt KMaxArgC=25;
29 static char* wcstombs_alloc (const wchar_t* aString)
34 size_t size = wcstombs(0, aString, 0);
35 char* buf = (char*)malloc(size * sizeof(char));
37 size = wcstombs(buf, aString, size);
38 if (size == (size_t) -1)
43 buf = (char*)realloc(buf, (size+1) * sizeof(char));
49 static wchar_t* allocCommandLine(const TDesC& aPath)
51 TInt cmdLength = User::CommandLineLength()+1; // for zero termination
52 TText16* cmdbuf = (TText16*)malloc(cmdLength*sizeof(TText16));
54 return (wchar_t*)cmdbuf; // we are just doomed, so give up now
56 TPtr16 cmdline(cmdbuf, cmdLength);
57 User::CommandLine(cmdline);
59 // The .EXE recogniser supplies a command line which is the name of the file,
60 // followed by a space. This is usually not what's wanted, so remove the
61 // filename if it is an exact match for the start of the command line.
63 if (cmdline.Find(aPath)==0)
65 cmdline.Delete(0, aPath.Length());
67 cmdline.ZeroTerminate();
68 return (wchar_t*)cmdbuf;
73 static wchar_t* allocCommandLine(const TDesC& aPath)
76 TInt cmdLength = me.CommandLineLength()+1; // for zero termination
77 TText16* cmdbuf = (TText16*)malloc(cmdLength*sizeof(TText16));
79 return (wchar_t*)cmdbuf; // we are just doomed, so give up now
81 TPtr16 cmdline(cmdbuf, cmdLength);
82 me.CommandLine(cmdline);
84 // The .EXE recogniser supplies a command line which is the name of the file,
85 // followed by a space. This is usually not what's wanted, so remove the
86 // filename if it is an exact match for the start of the command line.
88 if (cmdline.Find(aPath)==0)
90 cmdline.Delete(0, aPath.Length());
92 cmdline.ZeroTerminate();
93 return (wchar_t*)cmdbuf;
98 EXPORT_C void __crt0(int& argc, char**& argv, char**& envp)
100 // Find out the filename for argv[0]
102 TBuf16<KMaxFileName+1> exepath(RProcess().FileName());
104 // Sort out argc/argv, creating an array of pointers into a copy of
107 wchar_t* cmdbuf = allocCommandLine(exepath);
108 char* cmd = wcstombs_alloc(cmdbuf);
110 char* filename = wcstombs_alloc((const wchar_t *)exepath.PtrZ());
112 argv = (char**)calloc(KMaxArgC, sizeof(char*));
114 // Check for memory allocation failures.
115 if (argv==0 || cmd==0 || filename== 0)
117 // Free any memory that could have been allocated before returning.
120 return; // it's basically doomed at this point anyway
123 // Split the command line into the separate arguments
124 // Follow the stdarg.c rules in the Win32 runtime, namely
125 // 1. space and tab are whitespace separators, except inside "..." pairs
126 // 2. strings of \ are literal unless followed by " (see below)
127 // 3. a pair of "" in a quoted string is a literal "
129 const char KSpace= ' ';
130 const char KTab = '\t';
131 const char KQuote= '"';
132 const char KSlash= '\\';
143 // skip leading whitespace
146 while (c && (c==KSpace || c==KTab));
148 // update the argv,argc
149 if (c=='\0' || argc>=KMaxArgC)
155 // copy the argument from p to q
156 for (;c!='\0';c=*p++)
159 // The UNC filenames format used, e.g. \\host\dir\file
160 // Hence the rather odd rules: for N>=0
161 // 2N+1 slash + " => N slash + literal "
162 // 2N slash + " => N slash, start/end quoted substring
163 // N slash + ? => N slash + ?
168 *q++=c; // copy the slashes (might be too many)
176 q-=(slashcount-(slashcount/2)); // slashes followed by quote - adjust
179 *q++=c; // literal quote
182 if (quoted && *p==KQuote)
185 *q++=c; // "" inside quoted section = literal quote
191 if (!quoted && (c==KSpace || c==KTab))
195 *q++='\0'; // terminate the copy
198 break; // end of command line
201 // sort out the environment
206 EXPORT_C void __crt0(int& argc, wchar_t**& wargv, wchar_t**& wenvp)
208 // Find out the filename for argv[0]
210 TBuf16<KMaxFileName+1> exepath(RProcess().FileName());
212 // Sort out argc/argv, creating an array of pointers into a copy of
215 wchar_t* cmd = allocCommandLine(exepath);
216 wchar_t* filename = wcsdup((const wchar_t *)exepath.PtrZ());
217 wargv = (wchar_t**)calloc(KMaxArgC, sizeof(wchar_t*));
219 // Check for memory allocation failures.
220 if (wargv==0 || cmd==0 || filename== 0)
222 // Free any memory that could have been allocated before returning.
225 return; // it's basically doomed at this point anyway
228 // Split the command line into the separate arguments
229 // Follow the stdarg.c rules in the Win32 runtime, namely
230 // 1. space and tab are whitespace separators, except inside "..." pairs
231 // 2. strings of \ are literal unless followed by " (see below)
232 // 3. a pair of "" in a quoted string is a literal "
234 const wchar_t KSpace= L' ';
235 const wchar_t KTab = L'\t';
236 const wchar_t KQuote= L'"';
237 const wchar_t KSlash= L'\\';
248 // skip leading whitespace
251 while (c && (c==KSpace || c==KTab));
253 // update the argv,argc
254 if (c=='\0' || argc>=KMaxArgC)
260 // copy the argument from p to q
261 for (;c!=L'\0';c=*p++)
264 // The UNC filenames format used, e.g. \\host\dir\file
265 // Hence the rather odd rules: for N>=0
266 // 2N+1 slash + " => N slash + literal "
267 // 2N slash + " => N slash, start/end quoted substring
268 // N slash + ? => N slash + ?
273 *q++=c; // copy the slashes (might be too many)
281 q-=(slashcount-(slashcount/2)); // slashes followed by quote - adjust
284 *q++=c; // literal quote
287 if (quoted && *p==KQuote)
290 *q++=c; // "" inside quoted section = literal quote
296 if (!quoted && (c==KSpace || c==KTab))
300 *q++=L'\0'; // terminate the copy
303 break; // end of command line
306 // sort out the environment