comparison src/windows/bin/cmdtoargs.c @ 10890:e7c32c6758c0

8073773: Presume path preparedness Reviewed-by: darcy, dholmes, ahgross
author ksrini
date Wed, 04 Mar 2015 15:12:09 -0800
parents 5e769206f036
children b68d8ff43361
comparison
equal deleted inserted replaced
2:d74ee71fd759 3:ddff0f7fdd9c
51 } StdArg ; 51 } StdArg ;
52 #endif 52 #endif
53 static StdArg *stdargs; 53 static StdArg *stdargs;
54 static int stdargc; 54 static int stdargc;
55 55
56 static int copyCh(USHORT ch, char* dest) {
57 if (HIBYTE(ch) == 0) {
58 *dest = (char)ch;
59 return 1;
60 } else {
61 *((USHORT *)dest) = ch;
62 return 2;
63 }
64 }
65
56 static char* next_arg(char* cmdline, char* arg, jboolean* wildcard) { 66 static char* next_arg(char* cmdline, char* arg, jboolean* wildcard) {
57 67
58 char* src = cmdline; 68 char* src = cmdline;
59 char* dest = arg; 69 char* dest = arg;
60 jboolean separator = JNI_FALSE; 70 jboolean separator = JNI_FALSE;
61 int quotes = 0; 71 int quotes = 0;
62 int slashes = 0; 72 int slashes = 0;
63 73
64 char prev = 0; 74 // "prev"/"ch" may contain either a single byte, or a double byte
65 char ch = 0; 75 // character encoded in CP_ACP.
76 USHORT prev = 0;
77 USHORT ch = 0;
66 int i; 78 int i;
67 jboolean done = JNI_FALSE; 79 jboolean done = JNI_FALSE;
80 int charLength;
68 81
69 *wildcard = JNI_FALSE; 82 *wildcard = JNI_FALSE;
70 while ((ch = *src) != 0 && !done) { 83 while (!done) {
84 charLength = CharNextExA(CP_ACP, src, 0) - src;
85 if (charLength == 0) {
86 break;
87 } else if (charLength == 1) {
88 ch = (USHORT)(UCHAR)src[0];
89 } else {
90 ch = ((USHORT *)src)[0];
91 }
92
71 switch (ch) { 93 switch (ch) {
72 case '"': 94 case L'"':
73 if (separator) { 95 if (separator) {
74 done = JNI_TRUE; 96 done = JNI_TRUE;
75 break; 97 break;
76 } 98 }
77 if (prev == '\\') { 99 if (prev == L'\\') {
78 for (i = 1; i < slashes; i += 2) { 100 for (i = 1; i < slashes; i += 2) {
79 *dest++ = prev; 101 dest += copyCh(prev, dest);
80 } 102 }
81 if (slashes % 2 == 1) { 103 if (slashes % 2 == 1) {
82 *dest++ = ch; 104 dest += copyCh(ch, dest);
83 } else { 105 } else {
84 quotes++; 106 quotes++;
85 } 107 }
86 } else if (prev == '"' && quotes % 2 == 0) { 108 } else if (prev == L'"' && quotes % 2 == 0) {
87 quotes++; 109 quotes++;
88 *dest++ = ch; // emit every other consecutive quote 110 dest += copyCh(ch, dest); // emit every other consecutive quote
89 } else if (quotes == 0) { 111 } else if (quotes == 0) {
90 quotes++; // starting quote 112 quotes++; // starting quote
91 } else { 113 } else {
92 quotes--; // matching quote 114 quotes--; // matching quote
93 } 115 }
94 slashes = 0; 116 slashes = 0;
95 break; 117 break;
96 118
97 case '\\': 119 case L'\\':
98 slashes++; 120 slashes++;
99 if (separator) { 121 if (separator) {
100 done = JNI_TRUE; 122 done = JNI_TRUE;
101 separator = JNI_FALSE; 123 separator = JNI_FALSE;
102 } 124 }
103 break; 125 break;
104 126
105 case ' ': 127 case L' ':
106 case '\t': 128 case L'\t':
107 if (prev == '\\') { 129 if (prev == L'\\') {
108 for (i = 0 ; i < slashes; i++) { 130 for (i = 0 ; i < slashes; i++) {
109 *dest++ = prev; 131 dest += copyCh(prev, dest);
110 } 132 }
111 } 133 }
112 if (quotes % 2 == 1) { 134 if (quotes % 2 == 1) {
113 *dest++ = ch; 135 dest += copyCh(ch, dest);
114 } else { 136 } else {
115 separator = JNI_TRUE; 137 separator = JNI_TRUE;
116 } 138 }
117 slashes = 0; 139 slashes = 0;
118 break; 140 break;
119 141
120 case '*': 142 case L'*':
121 case '?': 143 case L'?':
122 if (separator) { 144 if (separator) {
123 done = JNI_TRUE; 145 done = JNI_TRUE;
124 separator = JNI_FALSE; 146 separator = JNI_FALSE;
125 break; 147 break;
126 } 148 }
127 if (quotes % 2 == 0) { 149 if (quotes % 2 == 0) {
128 *wildcard = JNI_TRUE; 150 *wildcard = JNI_TRUE;
129 } 151 }
130 if (prev == '\\') { 152 if (prev == L'\\') {
131 for (i = 0 ; i < slashes ; i++) { 153 for (i = 0 ; i < slashes ; i++) {
132 *dest++ = prev; 154 dest += copyCh(prev, dest);
133 } 155 }
134 } 156 }
135 *dest++ = ch; 157 dest += copyCh(ch, dest);
136 break; 158 break;
137 159
138 default: 160 default:
139 if (prev == '\\') { 161 if (prev == L'\\') {
140 for (i = 0 ; i < slashes ; i++) { 162 for (i = 0 ; i < slashes ; i++) {
141 *dest++ = prev; 163 dest += copyCh(prev, dest);
142 } 164 }
143 *dest++ = ch; 165 dest += copyCh(ch, dest);
144 } else if (separator) { 166 } else if (separator) {
145 done = JNI_TRUE; 167 done = JNI_TRUE;
146 } else { 168 } else {
147 *dest++ = ch; 169 dest += copyCh(ch, dest);
148 } 170 }
149 slashes = 0; 171 slashes = 0;
150 } 172 }
151 173
152 if (!done) { 174 if (!done) {
153 prev = ch; 175 prev = ch;
154 src++; 176 src += charLength;
155 } 177 }
156 } 178 }
157 if (prev == '\\') { 179 if (prev == L'\\') {
158 for (i = 0; i < slashes; i++) { 180 for (i = 0; i < slashes; i++) {
159 *dest++ = prev; 181 dest += copyCh(prev, dest);
160 } 182 }
161 } 183 }
162 *dest = 0; 184 *dest = 0;
163 return done ? src : NULL; 185 return done ? src : NULL;
164 } 186 }