1 /****************************************************************************** 2 * 3 * Module Name: asmain - Main module for the acpi source processor utility 4 * 5 *****************************************************************************/ 6 7 /* 8 * Copyright (C) 2000 - 2015, Intel Corp. 9 * All rights reserved. 10 * 11 * Redistribution and use in source and binary forms, with or without 12 * modification, are permitted provided that the following conditions 13 * are met: 14 * 1. Redistributions of source code must retain the above copyright 15 * notice, this list of conditions, and the following disclaimer, 16 * without modification. 17 * 2. Redistributions in binary form must reproduce at minimum a disclaimer 18 * substantially similar to the "NO WARRANTY" disclaimer below 19 * ("Disclaimer") and any redistribution must be conditioned upon 20 * including a substantially similar Disclaimer requirement for further 21 * binary redistribution. 22 * 3. Neither the names of the above-listed copyright holders nor the names 23 * of any contributors may be used to endorse or promote products derived 24 * from this software without specific prior written permission. 25 * 26 * Alternatively, this software may be distributed under the terms of the 27 * GNU General Public License ("GPL") version 2 as published by the Free 28 * Software Foundation. 29 * 30 * NO WARRANTY 31 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 32 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 33 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR 34 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 35 * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 36 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 37 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 38 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, 39 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING 40 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 41 * POSSIBILITY OF SUCH DAMAGES. 42 */ 43 44 #include "acpisrc.h" 45 #include "acapps.h" 46 47 /* Local prototypes */ 48 49 int 50 AsExaminePaths ( 51 ACPI_CONVERSION_TABLE *ConversionTable, 52 char *Source, 53 char *Target, 54 UINT32 *SourceFileType); 55 56 void 57 AsDisplayStats ( 58 void); 59 60 void 61 AsDisplayUsage ( 62 void); 63 64 /* Globals */ 65 66 UINT32 Gbl_Tabs = 0; 67 UINT32 Gbl_MissingBraces = 0; 68 UINT32 Gbl_NonAnsiComments = 0; 69 UINT32 Gbl_Files = 0; 70 UINT32 Gbl_WhiteLines = 0; 71 UINT32 Gbl_CommentLines = 0; 72 UINT32 Gbl_SourceLines = 0; 73 UINT32 Gbl_LongLines = 0; 74 UINT32 Gbl_TotalLines = 0; 75 UINT32 Gbl_TotalSize = 0; 76 UINT32 Gbl_HeaderLines = 0; 77 UINT32 Gbl_HeaderSize = 0; 78 void *Gbl_StructDefs = NULL; 79 80 struct stat Gbl_StatBuf; 81 char *Gbl_FileBuffer; 82 UINT32 Gbl_FileSize; 83 UINT32 Gbl_FileType; 84 BOOLEAN Gbl_VerboseMode = FALSE; 85 BOOLEAN Gbl_QuietMode = FALSE; 86 BOOLEAN Gbl_BatchMode = FALSE; 87 BOOLEAN Gbl_DebugStatementsMode = FALSE; 88 BOOLEAN Gbl_MadeChanges = FALSE; 89 BOOLEAN Gbl_Overwrite = FALSE; 90 BOOLEAN Gbl_WidenDeclarations = FALSE; 91 BOOLEAN Gbl_IgnoreLoneLineFeeds = FALSE; 92 BOOLEAN Gbl_HasLoneLineFeeds = FALSE; 93 BOOLEAN Gbl_Cleanup = FALSE; 94 BOOLEAN Gbl_IgnoreTranslationEscapes = FALSE; 95 96 #define AS_UTILITY_NAME "ACPI Source Code Conversion Utility" 97 #define AS_SUPPORTED_OPTIONS "cdhilqsuv^y" 98 99 100 /****************************************************************************** 101 * 102 * FUNCTION: AsExaminePaths 103 * 104 * DESCRIPTION: Source and Target pathname verification and handling 105 * 106 ******************************************************************************/ 107 108 int 109 AsExaminePaths ( 110 ACPI_CONVERSION_TABLE *ConversionTable, 111 char *Source, 112 char *Target, 113 UINT32 *SourceFileType) 114 { 115 int Status; 116 int Response; 117 118 119 Status = stat (Source, &Gbl_StatBuf); 120 if (Status) 121 { 122 printf ("Source path \"%s\" does not exist\n", Source); 123 return (-1); 124 } 125 126 /* Return the filetype -- file or a directory */ 127 128 *SourceFileType = 0; 129 if (Gbl_StatBuf.st_mode & S_IFDIR) 130 { 131 *SourceFileType = S_IFDIR; 132 } 133 134 /* 135 * If we are in no-output mode or in batch mode, we are done 136 */ 137 if ((ConversionTable->Flags & FLG_NO_FILE_OUTPUT) || 138 (Gbl_BatchMode)) 139 { 140 return (0); 141 } 142 143 if (!AcpiUtStricmp (Source, Target)) 144 { 145 printf ("Target path is the same as the source path, overwrite?\n"); 146 Response = getchar (); 147 148 /* Check response */ 149 150 if (Response != 'y') 151 { 152 return (-1); 153 } 154 155 Gbl_Overwrite = TRUE; 156 } 157 else 158 { 159 Status = stat (Target, &Gbl_StatBuf); 160 if (!Status) 161 { 162 printf ("Target path already exists, overwrite?\n"); 163 Response = getchar (); 164 165 /* Check response */ 166 167 if (Response != 'y') 168 { 169 return (-1); 170 } 171 } 172 } 173 174 return (0); 175 } 176 177 178 /****************************************************************************** 179 * 180 * FUNCTION: AsDisplayStats 181 * 182 * DESCRIPTION: Display global statistics gathered during translation 183 * 184 ******************************************************************************/ 185 186 void 187 AsDisplayStats ( 188 void) 189 { 190 191 if (Gbl_QuietMode) 192 { 193 return; 194 } 195 196 printf ("\nAcpiSrc statistics:\n\n"); 197 printf ("%8u Files processed\n", Gbl_Files); 198 199 if (!Gbl_Files) 200 { 201 return; 202 } 203 204 printf ("%8u Total bytes (%.1fK/file)\n", 205 Gbl_TotalSize, ((double) Gbl_TotalSize/Gbl_Files)/1024); 206 printf ("%8u Tabs found\n", Gbl_Tabs); 207 printf ("%8u Missing if/else/while braces\n", Gbl_MissingBraces); 208 printf ("%8u Non-ANSI // comments found\n", Gbl_NonAnsiComments); 209 printf ("%8u Total Lines\n", Gbl_TotalLines); 210 printf ("%8u Lines of code\n", Gbl_SourceLines); 211 printf ("%8u Lines of non-comment whitespace\n", Gbl_WhiteLines); 212 printf ("%8u Lines of comments\n", Gbl_CommentLines); 213 printf ("%8u Long lines found\n", Gbl_LongLines); 214 215 if (Gbl_WhiteLines > 0) 216 { 217 printf ("%8.1f Ratio of code to whitespace\n", 218 ((float) Gbl_SourceLines / (float) Gbl_WhiteLines)); 219 } 220 221 if ((Gbl_CommentLines + Gbl_NonAnsiComments) > 0) 222 { 223 printf ("%8.1f Ratio of code to comments\n", 224 ((float) Gbl_SourceLines / (float) (Gbl_CommentLines + Gbl_NonAnsiComments))); 225 } 226 227 if (!Gbl_TotalLines) 228 { 229 return; 230 } 231 232 printf (" %u%% code, %u%% comments, %u%% whitespace, %u%% headers\n", 233 (Gbl_SourceLines * 100) / Gbl_TotalLines, 234 (Gbl_CommentLines * 100) / Gbl_TotalLines, 235 (Gbl_WhiteLines * 100) / Gbl_TotalLines, 236 (Gbl_HeaderLines * 100) / Gbl_TotalLines); 237 return; 238 } 239 240 241 /****************************************************************************** 242 * 243 * FUNCTION: AsDisplayUsage 244 * 245 * DESCRIPTION: Usage message 246 * 247 ******************************************************************************/ 248 249 void 250 AsDisplayUsage ( 251 void) 252 { 253 254 ACPI_USAGE_HEADER ("acpisrc [-c|l|u] [-dsvy] <SourceDir> <DestinationDir>"); 255 256 ACPI_OPTION ("-c", "Generate cleaned version of the source"); 257 ACPI_OPTION ("-h", "Insert dual-license header into all modules"); 258 ACPI_OPTION ("-i", "Cleanup macro indentation"); 259 ACPI_OPTION ("-l", "Generate Linux version of the source"); 260 ACPI_OPTION ("-u", "Generate Custom source translation"); 261 262 ACPI_USAGE_TEXT ("\n"); 263 ACPI_OPTION ("-d", "Leave debug statements in code"); 264 ACPI_OPTION ("-s", "Generate source statistics only"); 265 ACPI_OPTION ("-v", "Display version information"); 266 ACPI_OPTION ("-vb", "Verbose mode"); 267 ACPI_OPTION ("-y", "Suppress file overwrite prompts"); 268 } 269 270 271 /****************************************************************************** 272 * 273 * FUNCTION: main 274 * 275 * DESCRIPTION: C main function 276 * 277 ******************************************************************************/ 278 279 int ACPI_SYSTEM_XFACE 280 main ( 281 int argc, 282 char *argv[]) 283 { 284 int j; 285 ACPI_CONVERSION_TABLE *ConversionTable = NULL; 286 char *SourcePath; 287 char *TargetPath; 288 UINT32 FileType; 289 290 291 ACPI_DEBUG_INITIALIZE (); /* For debug version only */ 292 AcpiOsInitialize (); 293 printf (ACPI_COMMON_SIGNON (AS_UTILITY_NAME)); 294 295 if (argc < 2) 296 { 297 AsDisplayUsage (); 298 return (0); 299 } 300 301 /* Command line options */ 302 303 while ((j = AcpiGetopt (argc, argv, AS_SUPPORTED_OPTIONS)) != ACPI_OPT_END) switch(j) 304 { 305 case 'l': 306 307 /* Linux code generation */ 308 309 printf ("Creating Linux source code\n"); 310 ConversionTable = &LinuxConversionTable; 311 Gbl_WidenDeclarations = TRUE; 312 Gbl_IgnoreLoneLineFeeds = TRUE; 313 break; 314 315 case 'c': 316 317 /* Cleanup code */ 318 319 printf ("Code cleanup\n"); 320 ConversionTable = &CleanupConversionTable; 321 Gbl_Cleanup = TRUE; 322 break; 323 324 case 'h': 325 326 /* Inject Dual-license header */ 327 328 printf ("Inserting Dual-license header to all modules\n"); 329 ConversionTable = &LicenseConversionTable; 330 break; 331 332 case 'i': 333 334 /* Cleanup wrong indent result */ 335 336 printf ("Cleaning up macro indentation\n"); 337 ConversionTable = &IndentConversionTable; 338 Gbl_IgnoreLoneLineFeeds = TRUE; 339 Gbl_IgnoreTranslationEscapes = TRUE; 340 break; 341 342 case 's': 343 344 /* Statistics only */ 345 346 break; 347 348 case 'u': 349 350 /* custom conversion */ 351 352 printf ("Custom source translation\n"); 353 ConversionTable = &CustomConversionTable; 354 break; 355 356 case 'v': 357 358 switch (AcpiGbl_Optarg[0]) 359 { 360 case '^': /* -v: (Version): signon already emitted, just exit */ 361 362 exit (0); 363 364 case 'b': 365 366 /* Verbose mode */ 367 368 Gbl_VerboseMode = TRUE; 369 break; 370 371 default: 372 373 printf ("Unknown option: -v%s\n", AcpiGbl_Optarg); 374 return (-1); 375 } 376 377 break; 378 379 case 'y': 380 381 /* Batch mode */ 382 383 Gbl_BatchMode = TRUE; 384 break; 385 386 case 'd': 387 388 /* Leave debug statements in */ 389 390 Gbl_DebugStatementsMode = TRUE; 391 break; 392 393 case 'q': 394 395 /* Quiet mode */ 396 397 Gbl_QuietMode = TRUE; 398 break; 399 400 default: 401 402 AsDisplayUsage (); 403 return (-1); 404 } 405 406 407 SourcePath = argv[AcpiGbl_Optind]; 408 if (!SourcePath) 409 { 410 printf ("Missing source path\n"); 411 AsDisplayUsage (); 412 return (-1); 413 } 414 415 TargetPath = argv[AcpiGbl_Optind+1]; 416 417 if (!ConversionTable) 418 { 419 /* Just generate statistics. Ignore target path */ 420 421 TargetPath = SourcePath; 422 423 printf ("Source code statistics only\n"); 424 ConversionTable = &StatsConversionTable; 425 } 426 else if (!TargetPath) 427 { 428 TargetPath = SourcePath; 429 } 430 431 if (Gbl_DebugStatementsMode) 432 { 433 ConversionTable->SourceFunctions &= ~CVT_REMOVE_DEBUG_MACROS; 434 } 435 436 /* Check source and target paths and files */ 437 438 if (AsExaminePaths (ConversionTable, SourcePath, TargetPath, &FileType)) 439 { 440 return (-1); 441 } 442 443 /* Source/target can be either directories or a files */ 444 445 if (FileType == S_IFDIR) 446 { 447 /* Process the directory tree */ 448 449 AsProcessTree (ConversionTable, SourcePath, TargetPath); 450 } 451 else 452 { 453 /* Process a single file */ 454 455 /* Differentiate between source and header files */ 456 457 if (strstr (SourcePath, ".h")) 458 { 459 AsProcessOneFile (ConversionTable, NULL, TargetPath, 0, SourcePath, FILE_TYPE_HEADER); 460 } 461 else if (strstr (SourcePath, ".c")) 462 { 463 AsProcessOneFile (ConversionTable, NULL, TargetPath, 0, SourcePath, FILE_TYPE_SOURCE); 464 } 465 else if (strstr (SourcePath, ".patch")) 466 { 467 AsProcessOneFile (ConversionTable, NULL, TargetPath, 0, SourcePath, FILE_TYPE_PATCH); 468 } 469 else 470 { 471 printf ("Unknown file type - %s\n", SourcePath); 472 } 473 } 474 475 /* Always display final summary and stats */ 476 477 AsDisplayStats (); 478 479 return (0); 480 } 481