VirtualBox

source: kBuild/trunk/src/lib/startuphacks-win.c@ 3646

Last change on this file since 3646 was 3645, checked in by bird, 6 months ago

lib/startuphacks-win.c: UCRT adjustments.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 6.4 KB
Line 
1/* $Id: startuphacks-win.c 3645 2024-11-03 02:32:49Z bird $ */
2/** @file
3 * kBuild - Alternative argument parser for the windows startup code.
4 */
5
6/*
7 * Copyright (c) 2006-2024 knut st. osmundsen <[email protected]>
8 *
9 * parse_args(): Copyright (c) 1992-1998 by Eberhard Mattes
10 *
11 *
12 * This file is part of kBuild.
13 *
14 * kBuild is free software; you can redistribute it and/or modify
15 * it under the terms of the GNU General Public License as published by
16 * the Free Software Foundation; either version 2 of the License, or
17 * (at your option) any later version.
18 *
19 * kBuild is distributed in the hope that it will be useful,
20 * but WITHOUT ANY WARRANTY; without even the implied warranty of
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22 * GNU General Public License for more details.
23 *
24 * You should have received a copy of the GNU General Public License
25 * along with kBuild; if not, write to the Free Software
26 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
27 *
28 */
29
30/*******************************************************************************
31* Header Files *
32*******************************************************************************/
33#include <stdlib.h>
34#include <malloc.h>
35#include <Windows.h>
36#if _MSC_VER >= 1400
37# include <vcruntime_startup.h>
38#endif
39
40
41/*******************************************************************************
42* Internal Functions *
43*******************************************************************************/
44static int parse_args(const char *pszSrc, char **argv, char *pchPool);
45
46
47/*******************************************************************************
48* Global Variables *
49*******************************************************************************/
50/** argument count found by parse_args(). */
51static int g_cArgs = 0;
52/** the argument vector, for __getmainargs(). */
53static char **g_papszArgs = NULL;
54
55
56#if _MSC_VER >= 1400
57int __cdecl _configure_narrow_argv(_crt_argv_mode const mode)
58#else
59int __cdecl _setargv(void)
60#endif
61{
62 static char s_szProgramName[MAX_PATH + 1];
63 const char *pszCmdLine;
64 char *pszCmdLineBuf;
65 int cb;
66
67 /*
68 * Set the program name.
69 */
70 GetModuleFileName(NULL, s_szProgramName, MAX_PATH);
71 s_szProgramName[MAX_PATH] = '\0';
72#if _MSC_VER >= 1400
73 _pgmptr = s_szProgramName;
74 (void)mode;
75#endif
76
77 /*
78 * Get the commandline, use the program name if nothings available.
79 */
80 pszCmdLine = (const char *)GetCommandLineA();
81 if (!pszCmdLine || !*pszCmdLine)
82 pszCmdLine = s_szProgramName;
83
84 /*
85 * Parse the argument commandline emitting the unix argument vector.
86 */
87 cb = parse_args(pszCmdLine, NULL, NULL);
88 g_papszArgs = malloc(sizeof(*g_papszArgs) * (g_cArgs + 2));
89 if (!g_papszArgs)
90 return _MSC_VER >= 1400 ? ENOMEM : -1;
91 pszCmdLineBuf = malloc(cb);
92 if (!pszCmdLineBuf)
93 return _MSC_VER >= 1400 ? ENOMEM : -1;
94 parse_args(pszCmdLine, g_papszArgs, pszCmdLineBuf);
95 g_papszArgs[g_cArgs] = g_papszArgs[g_cArgs + 1] = NULL;
96
97 /* set return variables */
98 __argc = g_cArgs;
99 __argv = g_papszArgs;
100 return 0;
101}
102#if _MSC_VER >= 1400
103int (__cdecl * __imp__configure_narrow_argv)(_crt_argv_mode) = _configure_narrow_argv;
104#endif
105
106
107#if _MSC_VER < 1400
108/* when linking with the crtexe.c, the __getmainargs() call will redo the _setargv job inside the msvc*.dll. */
109int __cdecl __getmainargs(int *pargc, char ***pargv, char ***penvp, int dowildcard, /*_startupinfo*/ void *startinfo)
110{
111 __argc = *pargc = g_cArgs;
112 __argv = *pargv = g_papszArgs;
113 *penvp = _environ;
114 return 0;
115}
116
117# if defined(_M_IX86)
118int (__cdecl * _imp____getmainargs)(int *, char ***, char ***, int, /*_startupinfo*/ void *) = __getmainargs;
119# else
120int (__cdecl * __imp___getmainargs)(int *, char ***, char ***, int, /*_startupinfo*/ void *) = __getmainargs;
121# endif
122#endif
123
124
125/**
126 * Parses the argument string passed in as pszSrc.
127 *
128 * @returns size of the processed arguments.
129 * @param pszSrc Pointer to the commandline that's to be parsed.
130 * @param argv Pointer to argument vector to put argument pointers in. NULL allowed.
131 * @param pchPool Pointer to memory pchPool to put the arguments into. NULL allowed.
132 */
133static int parse_args(const char *pszSrc, char **argv, char *pchPool)
134{
135 int bs;
136 char chQuote;
137 char *pfFlags;
138 int cbArgs;
139
140#define PUTC(c) do { ++cbArgs; if (pchPool != NULL) *pchPool++ = (c); } while (0)
141#define PUTV do { ++g_cArgs; if (argv != NULL) *argv++ = pchPool; } while (0)
142#define WHITE(c) ((c) == ' ' || (c) == '\t')
143
144#define _ARG_DQUOTE 0x01 /* Argument quoted (") */
145#define _ARG_RESPONSE 0x02 /* Argument read from response file */
146#define _ARG_WILDCARD 0x04 /* Argument expanded from wildcard */
147#define _ARG_ENV 0x08 /* Argument from environment */
148#define _ARG_NONZERO 0x80 /* Always set, to avoid end of string */
149
150 g_cArgs = 0; cbArgs = 0;
151
152#if 0
153 /* argv[0] */
154 PUTC((char)_ARG_NONZERO);
155 PUTV;
156 for (;;)
157 {
158 PUTC(*pszSrc);
159 if (*pszSrc == 0)
160 break;
161 ++pszSrc;
162 }
163 ++pszSrc;
164#endif
165
166 for (;;)
167 {
168 while (WHITE(*pszSrc))
169 ++pszSrc;
170 if (*pszSrc == 0)
171 break;
172 pfFlags = pchPool;
173 PUTC((char)_ARG_NONZERO);
174 PUTV;
175 bs = 0; chQuote = 0;
176 for (;;)
177 {
178 if (!chQuote ? (*pszSrc == '"' || *pszSrc == '\'') : *pszSrc == chQuote)
179 {
180 while (bs >= 2)
181 {
182 PUTC('\\');
183 bs -= 2;
184 }
185 if (bs & 1)
186 PUTC(*pszSrc);
187 else
188 {
189 chQuote = chQuote ? 0 : *pszSrc;
190 if (pfFlags != NULL)
191 *pfFlags |= _ARG_DQUOTE;
192 }
193 bs = 0;
194 }
195 else if (*pszSrc == '\\')
196 ++bs;
197 else
198 {
199 while (bs != 0)
200 {
201 PUTC('\\');
202 --bs;
203 }
204 if (*pszSrc == 0 || (WHITE(*pszSrc) && !chQuote))
205 break;
206 PUTC(*pszSrc);
207 }
208 ++pszSrc;
209 }
210 PUTC(0);
211 }
212 return cbArgs;
213}
214
Note: See TracBrowser for help on using the repository browser.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette