1 /****************************************************************************** 2 * 3 * Module Name: aslascii - ASCII detection and support routines 4 * 5 *****************************************************************************/ 6 7 /* 8 * Copyright (C) 2000 - 2022, 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 MERCHANTABILITY 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 "aslcompiler.h" 45 #include <actables.h> 46 #include <acapps.h> 47 48 #define _COMPONENT ACPI_COMPILER 49 ACPI_MODULE_NAME ("aslascii") 50 51 52 /* Local prototypes */ 53 54 static void 55 FlConsumeAnsiComment ( 56 FILE *Handle, 57 ASL_FILE_STATUS *Status); 58 59 static void 60 FlConsumeNewComment ( 61 FILE *Handle, 62 ASL_FILE_STATUS *Status); 63 64 65 /******************************************************************************* 66 * 67 * FUNCTION: FlIsFileAsciiSource 68 * 69 * PARAMETERS: Filename - Full input filename 70 * DisplayErrors - TRUE if error messages desired 71 * 72 * RETURN: Status 73 * 74 * DESCRIPTION: Verify that the input file is entirely ASCII. Ignores characters 75 * within comments. Note: does not handle nested comments and does 76 * not handle comment delimiters within string literals. However, 77 * on the rare chance this happens and an invalid character is 78 * missed, the parser will catch the error by failing in some 79 * spectacular manner. 80 * 81 ******************************************************************************/ 82 83 ACPI_STATUS 84 FlIsFileAsciiSource ( 85 char *Filename, 86 BOOLEAN DisplayErrors) 87 { 88 UINT8 Byte; 89 UINT32 BadBytes = 0; 90 BOOLEAN OpeningComment = FALSE; 91 ASL_FILE_STATUS Status; 92 FILE *Handle; 93 94 95 /* Open file in text mode so file offset is always accurate */ 96 97 Handle = fopen (Filename, "rb"); 98 if (!Handle) 99 { 100 perror ("Could not open input file"); 101 return (AE_ERROR); 102 } 103 104 Status.Line = 1; 105 Status.Offset = 0; 106 107 /* Read the entire file */ 108 109 while (fread (&Byte, 1, 1, Handle) == 1) 110 { 111 /* Ignore comment fields (allow non-ASCII within) */ 112 113 if (OpeningComment) 114 { 115 /* Check for second comment open delimiter */ 116 117 if (Byte == '*') 118 { 119 FlConsumeAnsiComment (Handle, &Status); 120 } 121 122 if (Byte == '/') 123 { 124 FlConsumeNewComment (Handle, &Status); 125 } 126 127 /* Reset */ 128 129 OpeningComment = FALSE; 130 } 131 else if (Byte == '/') 132 { 133 OpeningComment = TRUE; 134 } 135 136 /* Check for an ASCII character */ 137 138 if (!ACPI_IS_ASCII (Byte)) 139 { 140 if ((BadBytes < 10) && (DisplayErrors)) 141 { 142 AcpiOsPrintf ( 143 "Found non-ASCII character in source text: " 144 "0x%2.2X in line %u, file offset 0x%2.2X\n", 145 Byte, Status.Line, Status.Offset); 146 } 147 BadBytes++; 148 } 149 150 /* Ensure character is either printable or a "space" char */ 151 152 else if (!isprint (Byte) && !isspace (Byte)) 153 { 154 if ((BadBytes < 10) && (DisplayErrors)) 155 { 156 AcpiOsPrintf ( 157 "Found invalid character in source text: " 158 "0x%2.2X in line %u, file offset 0x%2.2X\n", 159 Byte, Status.Line, Status.Offset); 160 } 161 BadBytes++; 162 } 163 164 /* Update line counter as necessary */ 165 166 if (Byte == 0x0A) 167 { 168 Status.Line++; 169 } 170 171 Status.Offset++; 172 } 173 174 fclose (Handle); 175 176 /* Were there any non-ASCII characters in the file? */ 177 178 if (BadBytes) 179 { 180 fprintf (stderr, 181 "File appears to be binary: found %u non-ASCII characters, disassembling\n", 182 BadBytes); 183 if (DisplayErrors) 184 { 185 AcpiOsPrintf ( 186 "Total %u invalid characters found in input source text, " 187 "could be a binary file\n", BadBytes); 188 AslError (ASL_ERROR, ASL_MSG_NON_ASCII, NULL, Filename); 189 } 190 191 return (AE_BAD_CHARACTER); 192 } 193 194 /* File is OK (100% ASCII) */ 195 196 return (AE_OK); 197 } 198 199 200 /******************************************************************************* 201 * 202 * FUNCTION: FlConsumeAnsiComment 203 * 204 * PARAMETERS: Handle - Open input file 205 * Status - File current status struct 206 * 207 * RETURN: Number of lines consumed 208 * 209 * DESCRIPTION: Step over a normal slash-star type comment 210 * 211 ******************************************************************************/ 212 213 static void 214 FlConsumeAnsiComment ( 215 FILE *Handle, 216 ASL_FILE_STATUS *Status) 217 { 218 UINT8 Byte; 219 BOOLEAN ClosingComment = FALSE; 220 221 222 while (fread (&Byte, 1, 1, Handle) == 1) 223 { 224 /* Scan until comment close is found */ 225 226 if (ClosingComment) 227 { 228 if (Byte == '/') 229 { 230 Status->Offset++; 231 return; 232 } 233 234 if (Byte != '*') 235 { 236 /* Reset */ 237 238 ClosingComment = FALSE; 239 } 240 } 241 else if (Byte == '*') 242 { 243 ClosingComment = TRUE; 244 } 245 246 /* Maintain line count */ 247 248 if (Byte == 0x0A) 249 { 250 Status->Line++; 251 } 252 253 Status->Offset++; 254 } 255 } 256 257 258 /******************************************************************************* 259 * 260 * FUNCTION: FlConsumeNewComment 261 * 262 * PARAMETERS: Handle - Open input file 263 * Status - File current status struct 264 * 265 * RETURN: Number of lines consumed 266 * 267 * DESCRIPTION: Step over a slash-slash type of comment 268 * 269 ******************************************************************************/ 270 271 static void 272 FlConsumeNewComment ( 273 FILE *Handle, 274 ASL_FILE_STATUS *Status) 275 { 276 UINT8 Byte; 277 278 279 while (fread (&Byte, 1, 1, Handle) == 1) 280 { 281 Status->Offset++; 282 283 /* Comment ends at newline */ 284 285 if (Byte == 0x0A) 286 { 287 Status->Line++; 288 return; 289 } 290 } 291 } 292