• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright (c) 2017 The Khronos Group Inc.
3 //
4 // Licensed under the Apache License, Version 2.0 (the "License");
5 // you may not use this file except in compliance with the License.
6 // You may obtain a copy of the License at
7 //
8 //    http://www.apache.org/licenses/LICENSE-2.0
9 //
10 // Unless required by applicable law or agreed to in writing, software
11 // distributed under the License is distributed on an "AS IS" BASIS,
12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 // See the License for the specific language governing permissions and
14 // limitations under the License.
15 //
16 #include "parseParameters.h"
17 
18 #include "errorHelpers.h"
19 #include "testHarness.h"
20 #include "ThreadPool.h"
21 
22 #include <iostream>
23 #include <sstream>
24 #include <sys/types.h>
25 #include <sys/stat.h>
26 #include <string.h>
27 
28 using namespace std;
29 
30 #define DEFAULT_COMPILATION_PROGRAM "cl_offline_compiler"
31 #define DEFAULT_SPIRV_VALIDATOR "spirv-val"
32 
33 CompilationMode gCompilationMode = kOnline;
34 CompilationCacheMode gCompilationCacheMode = kCacheModeCompileIfAbsent;
35 std::string gCompilationCachePath = ".";
36 std::string gCompilationProgram = DEFAULT_COMPILATION_PROGRAM;
37 bool gDisableSPIRVValidation = false;
38 std::string gSPIRVValidator = DEFAULT_SPIRV_VALIDATOR;
39 
helpInfo()40 void helpInfo()
41 {
42     log_info(
43         R"(Common options:
44     -h, --help
45         This help
46     --compilation-mode <mode>
47         Specify a compilation mode.  Mode can be:
48             online     Use online compilation (default)
49             binary     Use binary offline compilation
50             spir-v     Use SPIR-V offline compilation
51 
52 For offline compilation (binary and spir-v modes) only:
53     --compilation-cache-mode <cache-mode>
54         Specify a compilation caching mode:
55             compile-if-absent
56                 Read from cache if already populated, or else perform
57                 offline compilation (default)
58             force-read
59                 Force reading from the cache
60             overwrite
61                 Disable reading from the cache
62             dump-cl-files
63                 Dumps the .cl and build .options files used by the test suite
64     --compilation-cache-path <path>
65         Path for offline compiler output and CL source
66     --compilation-program <prog>
67         Program to use for offline compilation, defaults to:
68             )" DEFAULT_COMPILATION_PROGRAM R"(
69 
70 For spir-v mode only:
71     --disable-spirv-validation
72         Disable validation of SPIR-V using the SPIR-V validator
73     --spirv-validator
74         Path for SPIR-V validator, defaults to )" DEFAULT_SPIRV_VALIDATOR "\n"
75         "\n");
76 }
77 
parseCustomParam(int argc,const char * argv[],const char * ignore)78 int parseCustomParam(int argc, const char *argv[], const char *ignore)
79 {
80     int delArg = 0;
81 
82     for (int i = 1; i < argc; i++)
83     {
84         if (ignore != 0)
85         {
86             // skip parameters that require special/different treatment in
87             // application (generic interpretation and parameter removal will
88             // not be performed)
89             const char *ptr = strstr(ignore, argv[i]);
90             if (ptr != 0 && (ptr == ignore || ptr[-1] == ' ')
91                 && // first on list or ' ' before
92                 (ptr[strlen(argv[i])] == 0
93                  || ptr[strlen(argv[i])] == ' ')) // last on list or ' ' after
94                 continue;
95         }
96 
97         delArg = 0;
98 
99         if (strcmp(argv[i], "-h") == 0 || strcmp(argv[i], "--help") == 0)
100         {
101             // Note: we don't increment delArg to delete this argument,
102             // to allow the caller's argument parsing routine to see the
103             // option and print its own help.
104             helpInfo();
105         }
106         else if (!strcmp(argv[i], "--compilation-mode"))
107         {
108             delArg++;
109             if ((i + 1) < argc)
110             {
111                 delArg++;
112                 const char *mode = argv[i + 1];
113 
114                 if (!strcmp(mode, "online"))
115                 {
116                     gCompilationMode = kOnline;
117                 }
118                 else if (!strcmp(mode, "binary"))
119                 {
120                     gCompilationMode = kBinary;
121                 }
122                 else if (!strcmp(mode, "spir-v"))
123                 {
124                     gCompilationMode = kSpir_v;
125                 }
126                 else
127                 {
128                     log_error("Compilation mode not recognized: %s\n", mode);
129                     return -1;
130                 }
131                 log_info("Compilation mode specified: %s\n", mode);
132             }
133             else
134             {
135                 log_error("Compilation mode parameters are incorrect. Usage:\n"
136                           "  --compilation-mode <online|binary|spir-v>\n");
137                 return -1;
138             }
139         }
140         else if (!strcmp(argv[i], "--compilation-cache-mode"))
141         {
142             delArg++;
143             if ((i + 1) < argc)
144             {
145                 delArg++;
146                 const char *mode = argv[i + 1];
147 
148                 if (!strcmp(mode, "compile-if-absent"))
149                 {
150                     gCompilationCacheMode = kCacheModeCompileIfAbsent;
151                 }
152                 else if (!strcmp(mode, "force-read"))
153                 {
154                     gCompilationCacheMode = kCacheModeForceRead;
155                 }
156                 else if (!strcmp(mode, "overwrite"))
157                 {
158                     gCompilationCacheMode = kCacheModeOverwrite;
159                 }
160                 else if (!strcmp(mode, "dump-cl-files"))
161                 {
162                     gCompilationCacheMode = kCacheModeDumpCl;
163                 }
164                 else
165                 {
166                     log_error("Compilation cache mode not recognized: %s\n",
167                               mode);
168                     return -1;
169                 }
170                 log_info("Compilation cache mode specified: %s\n", mode);
171             }
172             else
173             {
174                 log_error(
175                     "Compilation cache mode parameters are incorrect. Usage:\n"
176                     "  --compilation-cache-mode "
177                     "<compile-if-absent|force-read|overwrite>\n");
178                 return -1;
179             }
180         }
181         else if (!strcmp(argv[i], "--compilation-cache-path"))
182         {
183             delArg++;
184             if ((i + 1) < argc)
185             {
186                 delArg++;
187                 gCompilationCachePath = argv[i + 1];
188             }
189             else
190             {
191                 log_error("Path argument for --compilation-cache-path was not "
192                           "specified.\n");
193                 return -1;
194             }
195         }
196         else if (!strcmp(argv[i], "--compilation-program"))
197         {
198             delArg++;
199             if ((i + 1) < argc)
200             {
201                 delArg++;
202                 gCompilationProgram = argv[i + 1];
203             }
204             else
205             {
206                 log_error("Program argument for --compilation-program was not "
207                           "specified.\n");
208                 return -1;
209             }
210         }
211         else if (!strcmp(argv[i], "--disable-spirv-validation"))
212         {
213             delArg++;
214             gDisableSPIRVValidation = true;
215         }
216         else if (!strcmp(argv[i], "--spirv-validator"))
217         {
218             delArg++;
219             if ((i + 1) < argc)
220             {
221                 delArg++;
222                 gSPIRVValidator = argv[i + 1];
223             }
224             else
225             {
226                 log_error("Program argument for --spirv-validator was not "
227                           "specified.\n");
228                 return -1;
229             }
230         }
231 
232         // cleaning parameters from argv tab
233         for (int j = i; j < argc - delArg; j++) argv[j] = argv[j + delArg];
234         argc -= delArg;
235         i -= delArg;
236     }
237 
238     if ((gCompilationCacheMode == kCacheModeForceRead
239          || gCompilationCacheMode == kCacheModeOverwrite)
240         && gCompilationMode == kOnline)
241     {
242         log_error("Compilation cache mode can only be specified when using an "
243                   "offline compilation mode.\n");
244         return -1;
245     }
246 
247     return argc;
248 }
249 
is_power_of_two(int number)250 bool is_power_of_two(int number) { return number && !(number & (number - 1)); }
251 
parseWimpyReductionFactor(const char * & arg,int & wimpyReductionFactor)252 extern void parseWimpyReductionFactor(const char *&arg,
253                                       int &wimpyReductionFactor)
254 {
255     const char *arg_temp = strchr(&arg[1], ']');
256     if (arg_temp != 0)
257     {
258         int new_factor = atoi(&arg[1]);
259         arg = arg_temp; // Advance until ']'
260         if (is_power_of_two(new_factor))
261         {
262             log_info("\n Wimpy reduction factor changed from %d to %d \n",
263                      wimpyReductionFactor, new_factor);
264             wimpyReductionFactor = new_factor;
265         }
266         else
267         {
268             log_info("\n WARNING: Incorrect wimpy reduction factor %d, must be "
269                      "power of 2. The default value will be used.\n",
270                      new_factor);
271         }
272     }
273 }
274