xref: /netbsd-src/sys/external/bsd/acpica/dist/compiler/aslfiles.c (revision 987b04d624d6d5e25e3e80d683a4ebe80fe47dcf)
128c506b8Sjruoho /******************************************************************************
228c506b8Sjruoho  *
3ff4a156dSchristos  * Module Name: aslfiles - File support functions
428c506b8Sjruoho  *
528c506b8Sjruoho  *****************************************************************************/
628c506b8Sjruoho 
7124f4c82Sjruoho /*
82c7d7e3cSchristos  * Copyright (C) 2000 - 2023, Intel Corp.
928c506b8Sjruoho  * All rights reserved.
1028c506b8Sjruoho  *
11124f4c82Sjruoho  * Redistribution and use in source and binary forms, with or without
12124f4c82Sjruoho  * modification, are permitted provided that the following conditions
13124f4c82Sjruoho  * are met:
14124f4c82Sjruoho  * 1. Redistributions of source code must retain the above copyright
15124f4c82Sjruoho  *    notice, this list of conditions, and the following disclaimer,
16124f4c82Sjruoho  *    without modification.
17124f4c82Sjruoho  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
18124f4c82Sjruoho  *    substantially similar to the "NO WARRANTY" disclaimer below
19124f4c82Sjruoho  *    ("Disclaimer") and any redistribution must be conditioned upon
20124f4c82Sjruoho  *    including a substantially similar Disclaimer requirement for further
21124f4c82Sjruoho  *    binary redistribution.
22124f4c82Sjruoho  * 3. Neither the names of the above-listed copyright holders nor the names
23124f4c82Sjruoho  *    of any contributors may be used to endorse or promote products derived
24124f4c82Sjruoho  *    from this software without specific prior written permission.
2528c506b8Sjruoho  *
26124f4c82Sjruoho  * Alternatively, this software may be distributed under the terms of the
27124f4c82Sjruoho  * GNU General Public License ("GPL") version 2 as published by the Free
28124f4c82Sjruoho  * Software Foundation.
2928c506b8Sjruoho  *
30124f4c82Sjruoho  * NO WARRANTY
31124f4c82Sjruoho  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
32124f4c82Sjruoho  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
3398244dcfSchristos  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
34124f4c82Sjruoho  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
35124f4c82Sjruoho  * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
36124f4c82Sjruoho  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
37124f4c82Sjruoho  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
38124f4c82Sjruoho  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
39124f4c82Sjruoho  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
40124f4c82Sjruoho  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
41124f4c82Sjruoho  * POSSIBILITY OF SUCH DAMAGES.
42124f4c82Sjruoho  */
4328c506b8Sjruoho 
4428c506b8Sjruoho #include "aslcompiler.h"
4528c506b8Sjruoho #include "acapps.h"
4628c506b8Sjruoho 
4728c506b8Sjruoho #define _COMPONENT          ACPI_COMPILER
4828c506b8Sjruoho         ACPI_MODULE_NAME    ("aslfiles")
4928c506b8Sjruoho 
5028c506b8Sjruoho /* Local prototypes */
5128c506b8Sjruoho 
529b9ee194Schristos static FILE *
5328c506b8Sjruoho FlOpenIncludeWithPrefix (
5428c506b8Sjruoho     char                    *PrefixDir,
559b9ee194Schristos     ACPI_PARSE_OBJECT       *Op,
5628c506b8Sjruoho     char                    *Filename);
5728c506b8Sjruoho 
587ab6b89bSchristos static BOOLEAN
597ab6b89bSchristos FlInputFileExists (
607ab6b89bSchristos     char                    *InputFilename);
617ab6b89bSchristos 
6228c506b8Sjruoho #ifdef ACPI_OBSOLETE_FUNCTIONS
6328c506b8Sjruoho ACPI_STATUS
6428c506b8Sjruoho FlParseInputPathname (
6528c506b8Sjruoho     char                    *InputFilename);
6628c506b8Sjruoho #endif
6728c506b8Sjruoho 
6828c506b8Sjruoho 
6928c506b8Sjruoho /*******************************************************************************
7028c506b8Sjruoho  *
715b948c02Schristos  * FUNCTION:    FlInitOneFile
725b948c02Schristos  *
735b948c02Schristos  * PARAMETERS:  InputFilename       - The user-specified ASL source file to be
745b948c02Schristos  *                                    compiled
755b948c02Schristos  *
765b948c02Schristos  * RETURN:      Status
775b948c02Schristos  *
785b948c02Schristos  * DESCRIPTION: Initialize global file structure for one input file. This file
795b948c02Schristos  *              structure contains references to input, output, debugging, and
805b948c02Schristos  *              other miscellaneous files that are associated for a single
815b948c02Schristos  *              input ASL file.
825b948c02Schristos  *
835b948c02Schristos  ******************************************************************************/
845b948c02Schristos 
855b948c02Schristos ACPI_STATUS
865b948c02Schristos FlInitOneFile (
875b948c02Schristos     char                    *InputFilename)
885b948c02Schristos {
895b948c02Schristos     UINT32                  i;
905b948c02Schristos     ASL_GLOBAL_FILE_NODE    *NewFileNode;
915b948c02Schristos 
925b948c02Schristos 
935b948c02Schristos     if (FlInputFileExists (InputFilename))
945b948c02Schristos     {
955b948c02Schristos         AslError (ASL_ERROR, ASL_MSG_DUPLICATE_INPUT_FILE, NULL, InputFilename);
965b948c02Schristos         return (AE_ALREADY_EXISTS);
975b948c02Schristos     }
985b948c02Schristos 
995b948c02Schristos     NewFileNode = ACPI_CAST_PTR (ASL_GLOBAL_FILE_NODE,
1005b948c02Schristos         UtLocalCacheCalloc (sizeof (ASL_GLOBAL_FILE_NODE)));
1015b948c02Schristos 
1025b948c02Schristos     NewFileNode->ParserErrorDetected = FALSE;
1035b948c02Schristos     NewFileNode->Next = AslGbl_FilesList;
1045b948c02Schristos 
1055b948c02Schristos     AslGbl_FilesList = NewFileNode;
1065b948c02Schristos     AslGbl_Files = NewFileNode->Files;
1075b948c02Schristos 
1085b948c02Schristos     for (i = 0; i < ASL_NUM_FILES; i++)
1095b948c02Schristos     {
1105b948c02Schristos         AslGbl_Files[i].Handle = NULL;
1115b948c02Schristos         AslGbl_Files[i].Filename = NULL;
1125b948c02Schristos     }
1135b948c02Schristos 
1145b948c02Schristos     AslGbl_Files[ASL_FILE_STDOUT].Handle   = stdout;
1155b948c02Schristos     AslGbl_Files[ASL_FILE_STDOUT].Filename = "STDOUT";
1165b948c02Schristos 
1175b948c02Schristos     if (AslGbl_VerboseErrors)
1185b948c02Schristos     {
1195b948c02Schristos         AslGbl_Files[ASL_FILE_STDERR].Handle = stderr;
1205b948c02Schristos     }
1215b948c02Schristos     else
1225b948c02Schristos     {
1235b948c02Schristos         AslGbl_Files[ASL_FILE_STDERR].Handle = stdout;
1245b948c02Schristos     }
1255b948c02Schristos 
1265b948c02Schristos     AslGbl_Files[ASL_FILE_STDERR].Filename = "STDERR";
1275b948c02Schristos     return (AE_OK);
1285b948c02Schristos }
1295b948c02Schristos 
1305b948c02Schristos 
1315b948c02Schristos /*******************************************************************************
1325b948c02Schristos  *
1335b948c02Schristos  * FUNCTION:    FlInputFileExists
1345b948c02Schristos  *
1355b948c02Schristos  * PARAMETERS:  Filename       - File name to be searched
1365b948c02Schristos  *
1375b948c02Schristos  * RETURN:      Status
1385b948c02Schristos  *
1395b948c02Schristos  * DESCRIPTION: Returns true if the file name already exists.
1405b948c02Schristos  *
1415b948c02Schristos  ******************************************************************************/
1425b948c02Schristos 
1437ab6b89bSchristos static BOOLEAN
1445b948c02Schristos FlInputFileExists (
1455b948c02Schristos     char                    *Filename)
1465b948c02Schristos {
1475b948c02Schristos     ASL_GLOBAL_FILE_NODE    *Current = AslGbl_FilesList;
1485b948c02Schristos 
1495b948c02Schristos 
1505b948c02Schristos     while (Current)
1515b948c02Schristos     {
1525b948c02Schristos         if (!strcmp (Filename, Current->Files[ASL_FILE_INPUT].Filename))
1535b948c02Schristos         {
1545b948c02Schristos             return (TRUE);
1555b948c02Schristos         }
1565b948c02Schristos 
1575b948c02Schristos         Current = Current->Next;
1585b948c02Schristos     }
1595b948c02Schristos 
1605b948c02Schristos     return (FALSE);
1615b948c02Schristos }
1625b948c02Schristos 
1635b948c02Schristos 
1645b948c02Schristos /*******************************************************************************
1655b948c02Schristos  *
1665b948c02Schristos  * FUNCTION:    FlSwitchFileSet
1675b948c02Schristos  *
1685b948c02Schristos  * PARAMETERS:  Op        - Parse node for the LINE asl statement
1695b948c02Schristos  *
1705b948c02Schristos  * RETURN:      None.
1715b948c02Schristos  *
1725b948c02Schristos  * DESCRIPTION: Set the current line number
1735b948c02Schristos  *
1745b948c02Schristos  ******************************************************************************/
1755b948c02Schristos 
1765b948c02Schristos ASL_FILE_SWITCH_STATUS
1775b948c02Schristos FlSwitchFileSet (
1785b948c02Schristos     char                    *InputFilename)
1795b948c02Schristos {
1805b948c02Schristos     ASL_GLOBAL_FILE_NODE    *Current = AslGbl_FilesList;
1815b948c02Schristos     char                    *PrevFilename = Current->Files[ASL_FILE_INPUT].Filename;
1825b948c02Schristos 
1835b948c02Schristos 
1845b948c02Schristos     while (Current)
1855b948c02Schristos     {
1865b948c02Schristos         if (!strcmp(Current->Files[ASL_FILE_INPUT].Filename, InputFilename))
1875b948c02Schristos         {
1885b948c02Schristos             AslGbl_Files = Current->Files;
1895b948c02Schristos             AslGbl_TableSignature = Current->TableSignature;
1905b948c02Schristos             AslGbl_TableId = Current->TableId;
1915b948c02Schristos 
1925b948c02Schristos             if (!strcmp (InputFilename, PrevFilename))
1935b948c02Schristos             {
1945b948c02Schristos                 return (SWITCH_TO_SAME_FILE);
1955b948c02Schristos             }
1965b948c02Schristos             else
1975b948c02Schristos             {
1985b948c02Schristos                 return (SWITCH_TO_DIFFERENT_FILE);
1995b948c02Schristos             }
2005b948c02Schristos         }
2015b948c02Schristos 
2025b948c02Schristos         Current = Current->Next;
2035b948c02Schristos     }
2045b948c02Schristos 
2055b948c02Schristos     return (FILE_NOT_FOUND);
2065b948c02Schristos }
2075b948c02Schristos 
2085b948c02Schristos 
2095b948c02Schristos /*******************************************************************************
2105b948c02Schristos  *
2115b948c02Schristos  * FUNCTION:    FlGetFileHandle
2125b948c02Schristos  *
2135b948c02Schristos  * PARAMETERS:  OutFileId       - denotes file type of output handle
2145b948c02Schristos  *              InFileId        - denotes file type of the input Filename
2155b948c02Schristos  *              Filename
2165b948c02Schristos  *
2175b948c02Schristos  * RETURN:      File handle
2185b948c02Schristos  *
2195b948c02Schristos  * DESCRIPTION: Get the file handle for a particular filename/FileId. This
2205b948c02Schristos  *              function also allows the caller to specify the file Id of the
2215b948c02Schristos  *              desired type.
2225b948c02Schristos  *
2235b948c02Schristos  ******************************************************************************/
2245b948c02Schristos 
2255b948c02Schristos FILE *
2265b948c02Schristos FlGetFileHandle (
2275b948c02Schristos     UINT32                  OutFileId,
2285b948c02Schristos     UINT32                  InFileId,
2295b948c02Schristos     char                    *Filename)
2305b948c02Schristos {
2315b948c02Schristos     ASL_GLOBAL_FILE_NODE    *Current = AslGbl_FilesList;
2325b948c02Schristos 
2335b948c02Schristos 
2345b948c02Schristos     if (!Filename)
2355b948c02Schristos     {
2365b948c02Schristos         return (NULL);
2375b948c02Schristos     }
2385b948c02Schristos 
2395b948c02Schristos     while (Current)
2405b948c02Schristos     {
241*987b04d6Schristos         if (!((Current->FileType == ASL_INPUT_TYPE_ASCII_DATA) &&
242*987b04d6Schristos             (InFileId == ASL_FILE_SOURCE_OUTPUT)) &&
243*987b04d6Schristos             !strcmp (Current->Files[InFileId].Filename, Filename))
2445b948c02Schristos         {
2455b948c02Schristos             return (Current->Files[OutFileId].Handle);
2465b948c02Schristos         }
2475b948c02Schristos 
2485b948c02Schristos         Current = Current->Next;
2495b948c02Schristos     }
2505b948c02Schristos 
2515b948c02Schristos     return (NULL);
2525b948c02Schristos }
2535b948c02Schristos 
2545b948c02Schristos 
2555b948c02Schristos /*******************************************************************************
2565b948c02Schristos  *
2575b948c02Schristos  * FUNCTION:    FlGetFileNode
2585b948c02Schristos  *
2595b948c02Schristos  * PARAMETERS:  FileId        - File type (ID) of the input Filename
2605b948c02Schristos  *              Filename      - File to search for
2615b948c02Schristos  *
2625b948c02Schristos  * RETURN:      A global file node
2635b948c02Schristos  *
2645b948c02Schristos  * DESCRIPTION: Get the file node for a particular filename/FileId.
2655b948c02Schristos  *
2665b948c02Schristos  ******************************************************************************/
2675b948c02Schristos 
2685b948c02Schristos ASL_GLOBAL_FILE_NODE *
2695b948c02Schristos FlGetFileNode (
2705b948c02Schristos     UINT32                  FileId,
2715b948c02Schristos     char                    *Filename)
2725b948c02Schristos {
2735b948c02Schristos     ASL_GLOBAL_FILE_NODE    *Current = AslGbl_FilesList;
2745b948c02Schristos 
2755b948c02Schristos 
2765b948c02Schristos     if (!Filename)
2775b948c02Schristos     {
2785b948c02Schristos         return (NULL);
2795b948c02Schristos     }
2805b948c02Schristos 
2815b948c02Schristos     while (Current)
2825b948c02Schristos     {
2835b948c02Schristos         if (!strcmp (Current->Files[FileId].Filename, Filename))
2845b948c02Schristos         {
2855b948c02Schristos             return (Current);
2865b948c02Schristos         }
2875b948c02Schristos 
2885b948c02Schristos         Current = Current->Next;
2895b948c02Schristos     }
2905b948c02Schristos 
2915b948c02Schristos     return (NULL);
2925b948c02Schristos }
2935b948c02Schristos 
2945b948c02Schristos 
2955b948c02Schristos /*******************************************************************************
2965b948c02Schristos  *
2975b948c02Schristos  * FUNCTION:    FlGetCurrentFileNode
2985b948c02Schristos  *
2995b948c02Schristos  * PARAMETERS:  None
3005b948c02Schristos  *
3015b948c02Schristos  * RETURN:      Global file node
3025b948c02Schristos  *
3035b948c02Schristos  * DESCRIPTION: Get the current input file node
3045b948c02Schristos  *
3055b948c02Schristos  ******************************************************************************/
3065b948c02Schristos 
3075b948c02Schristos ASL_GLOBAL_FILE_NODE *
3085b948c02Schristos FlGetCurrentFileNode (
3095b948c02Schristos     void)
3105b948c02Schristos {
3111c663068Schristos     ASL_GLOBAL_FILE_NODE    *FileNode =
3121c663068Schristos         FlGetFileNode (ASL_FILE_INPUT,AslGbl_Files[ASL_FILE_INPUT].Filename);
3131c663068Schristos 
3141c663068Schristos 
3151c663068Schristos     if (!FileNode)
3161c663068Schristos     {
3171c663068Schristos         /*
3181c663068Schristos          * If the current file node does not exist after initializing the file
3191c663068Schristos          * node structures, something went wrong and this is an unrecoverable
3201c663068Schristos          * condition.
3211c663068Schristos          */
3221c663068Schristos         FlFileError (ASL_FILE_INPUT, ASL_MSG_COMPILER_INTERNAL);
3231c663068Schristos         AslAbort ();
3241c663068Schristos     }
3251c663068Schristos 
3261c663068Schristos     return (FileNode);
3275b948c02Schristos }
3285b948c02Schristos 
3295b948c02Schristos 
3305b948c02Schristos /*******************************************************************************
3315b948c02Schristos  *
33228c506b8Sjruoho  * FUNCTION:    FlSetLineNumber
33328c506b8Sjruoho  *
33428c506b8Sjruoho  * PARAMETERS:  Op        - Parse node for the LINE asl statement
33528c506b8Sjruoho  *
33628c506b8Sjruoho  * RETURN:      None.
33728c506b8Sjruoho  *
33828c506b8Sjruoho  * DESCRIPTION: Set the current line number
33928c506b8Sjruoho  *
34028c506b8Sjruoho  ******************************************************************************/
34128c506b8Sjruoho 
34228c506b8Sjruoho void
34328c506b8Sjruoho FlSetLineNumber (
344ff4a156dSchristos     UINT32                  LineNumber)
34528c506b8Sjruoho {
34628c506b8Sjruoho 
347ff4a156dSchristos     DbgPrint (ASL_PARSE_OUTPUT, "\n#line: New line number %u (old %u)\n",
3487efa3256Schristos          LineNumber, AslGbl_LogicalLineNumber);
349ff4a156dSchristos 
3507efa3256Schristos     AslGbl_CurrentLineNumber = LineNumber;
351ff4a156dSchristos }
352ff4a156dSchristos 
353ff4a156dSchristos 
354ff4a156dSchristos /*******************************************************************************
355ff4a156dSchristos  *
356ff4a156dSchristos  * FUNCTION:    FlSetFilename
357ff4a156dSchristos  *
358ff4a156dSchristos  * PARAMETERS:  Op        - Parse node for the LINE asl statement
359ff4a156dSchristos  *
360ff4a156dSchristos  * RETURN:      None.
361ff4a156dSchristos  *
362ff4a156dSchristos  * DESCRIPTION: Set the current filename
363ff4a156dSchristos  *
364ff4a156dSchristos  ******************************************************************************/
365ff4a156dSchristos 
366ff4a156dSchristos void
367ff4a156dSchristos FlSetFilename (
368ff4a156dSchristos     char                    *Filename)
369ff4a156dSchristos {
370ff4a156dSchristos 
371ff4a156dSchristos     DbgPrint (ASL_PARSE_OUTPUT, "\n#line: New filename %s (old %s)\n",
3727efa3256Schristos          Filename, AslGbl_Files[ASL_FILE_INPUT].Filename);
373ff4a156dSchristos 
374414ef032Schristos     /* No need to free any existing filename */
375414ef032Schristos 
3767efa3256Schristos     AslGbl_Files[ASL_FILE_INPUT].Filename = Filename;
37728c506b8Sjruoho }
37828c506b8Sjruoho 
37928c506b8Sjruoho 
38028c506b8Sjruoho /*******************************************************************************
38128c506b8Sjruoho  *
38228c506b8Sjruoho  * FUNCTION:    FlAddIncludeDirectory
38328c506b8Sjruoho  *
38428c506b8Sjruoho  * PARAMETERS:  Dir             - Directory pathname string
38528c506b8Sjruoho  *
38628c506b8Sjruoho  * RETURN:      None
38728c506b8Sjruoho  *
38828c506b8Sjruoho  * DESCRIPTION: Add a directory the list of include prefix directories.
38928c506b8Sjruoho  *
39028c506b8Sjruoho  ******************************************************************************/
39128c506b8Sjruoho 
39228c506b8Sjruoho void
39328c506b8Sjruoho FlAddIncludeDirectory (
39428c506b8Sjruoho     char                    *Dir)
39528c506b8Sjruoho {
39628c506b8Sjruoho     ASL_INCLUDE_DIR         *NewDir;
39728c506b8Sjruoho     ASL_INCLUDE_DIR         *NextDir;
39828c506b8Sjruoho     ASL_INCLUDE_DIR         *PrevDir = NULL;
39928c506b8Sjruoho     UINT32                  NeedsSeparator = 0;
40028c506b8Sjruoho     size_t                  DirLength;
40128c506b8Sjruoho 
40228c506b8Sjruoho 
40328c506b8Sjruoho     DirLength = strlen (Dir);
40428c506b8Sjruoho     if (!DirLength)
40528c506b8Sjruoho     {
40628c506b8Sjruoho         return;
40728c506b8Sjruoho     }
40828c506b8Sjruoho 
40928c506b8Sjruoho     /* Make sure that the pathname ends with a path separator */
41028c506b8Sjruoho 
41128c506b8Sjruoho     if ((Dir[DirLength-1] != '/') &&
41228c506b8Sjruoho         (Dir[DirLength-1] != '\\'))
41328c506b8Sjruoho     {
41428c506b8Sjruoho         NeedsSeparator = 1;
41528c506b8Sjruoho     }
41628c506b8Sjruoho 
4177efa3256Schristos     NewDir = ACPI_CAST_PTR (ASL_INCLUDE_DIR,
4187efa3256Schristos         UtLocalCacheCalloc (sizeof (ASL_INCLUDE_DIR)));
4197efa3256Schristos     NewDir->Dir = UtLocalCacheCalloc (DirLength + 1 + NeedsSeparator);
42028c506b8Sjruoho     strcpy (NewDir->Dir, Dir);
42128c506b8Sjruoho     if (NeedsSeparator)
42228c506b8Sjruoho     {
42328c506b8Sjruoho         strcat (NewDir->Dir, "/");
42428c506b8Sjruoho     }
42528c506b8Sjruoho 
42628c506b8Sjruoho     /*
42728c506b8Sjruoho      * Preserve command line ordering of -I options by adding new elements
42828c506b8Sjruoho      * at the end of the list
42928c506b8Sjruoho      */
4307efa3256Schristos     NextDir = AslGbl_IncludeDirList;
43128c506b8Sjruoho     while (NextDir)
43228c506b8Sjruoho     {
43328c506b8Sjruoho         PrevDir = NextDir;
43428c506b8Sjruoho         NextDir = NextDir->Next;
43528c506b8Sjruoho     }
43628c506b8Sjruoho 
43728c506b8Sjruoho     if (PrevDir)
43828c506b8Sjruoho     {
43928c506b8Sjruoho         PrevDir->Next = NewDir;
44028c506b8Sjruoho     }
44128c506b8Sjruoho     else
44228c506b8Sjruoho     {
4437efa3256Schristos         AslGbl_IncludeDirList = NewDir;
44428c506b8Sjruoho     }
44528c506b8Sjruoho }
44628c506b8Sjruoho 
44728c506b8Sjruoho 
44828c506b8Sjruoho /*******************************************************************************
44928c506b8Sjruoho  *
450ff4a156dSchristos  * FUNCTION:    FlMergePathnames
451ff4a156dSchristos  *
452ff4a156dSchristos  * PARAMETERS:  PrefixDir       - Prefix directory pathname. Can be NULL or
453ff4a156dSchristos  *                                a zero length string.
454ff4a156dSchristos  *              FilePathname    - The include filename from the source ASL.
455ff4a156dSchristos  *
456ff4a156dSchristos  * RETURN:      Merged pathname string
457ff4a156dSchristos  *
458ff4a156dSchristos  * DESCRIPTION: Merge two pathnames that (probably) have common elements, to
459ff4a156dSchristos  *              arrive at a minimal length string. Merge can occur if the
460ff4a156dSchristos  *              FilePathname is relative to the PrefixDir.
461ff4a156dSchristos  *
462ff4a156dSchristos  ******************************************************************************/
463ff4a156dSchristos 
464ff4a156dSchristos char *
465ff4a156dSchristos FlMergePathnames (
466ff4a156dSchristos     char                    *PrefixDir,
467ff4a156dSchristos     char                    *FilePathname)
468ff4a156dSchristos {
469ff4a156dSchristos     char                    *CommonPath;
470ff4a156dSchristos     char                    *Pathname;
471ff4a156dSchristos     char                    *LastElement;
472ff4a156dSchristos 
473ff4a156dSchristos 
474ff4a156dSchristos     DbgPrint (ASL_PARSE_OUTPUT, "Include: Prefix path - \"%s\"\n"
475ff4a156dSchristos         "Include: FilePathname - \"%s\"\n",
476ff4a156dSchristos          PrefixDir, FilePathname);
477ff4a156dSchristos 
478ff4a156dSchristos     /*
479ff4a156dSchristos      * If there is no prefix directory or if the file pathname is absolute,
480ff4a156dSchristos      * just return the original file pathname
481ff4a156dSchristos      */
482ff4a156dSchristos     if (!PrefixDir || (!*PrefixDir) ||
483ff4a156dSchristos         (*FilePathname == '/') ||
484ff4a156dSchristos          (FilePathname[1] == ':'))
485ff4a156dSchristos     {
48625666a51Schristos         Pathname = UtLocalCacheCalloc (strlen (FilePathname) + 1);
487ff4a156dSchristos         strcpy (Pathname, FilePathname);
488ff4a156dSchristos         goto ConvertBackslashes;
489ff4a156dSchristos     }
490ff4a156dSchristos 
491ff4a156dSchristos     /* Need a local copy of the prefix directory path */
492ff4a156dSchristos 
49325666a51Schristos     CommonPath = UtLocalCacheCalloc (strlen (PrefixDir) + 1);
494ff4a156dSchristos     strcpy (CommonPath, PrefixDir);
495ff4a156dSchristos 
496ff4a156dSchristos     /*
497ff4a156dSchristos      * Walk forward through the file path, and simultaneously backward
498ff4a156dSchristos      * through the prefix directory path until there are no more
499ff4a156dSchristos      * relative references at the start of the file path.
500ff4a156dSchristos      */
501ff4a156dSchristos     while (*FilePathname && (!strncmp (FilePathname, "../", 3)))
502ff4a156dSchristos     {
503ff4a156dSchristos         /* Remove last element of the prefix directory path */
504ff4a156dSchristos 
505ff4a156dSchristos         LastElement = strrchr (CommonPath, '/');
506ff4a156dSchristos         if (!LastElement)
507ff4a156dSchristos         {
508ff4a156dSchristos             goto ConcatenatePaths;
509ff4a156dSchristos         }
510ff4a156dSchristos 
511ff4a156dSchristos         *LastElement = 0;   /* Terminate CommonPath string */
512ff4a156dSchristos         FilePathname += 3;  /* Point to next path element */
513ff4a156dSchristos     }
514ff4a156dSchristos 
515ff4a156dSchristos     /*
516ff4a156dSchristos      * Remove the last element of the prefix directory path (it is the same as
517ff4a156dSchristos      * the first element of the file pathname), and build the final merged
518ff4a156dSchristos      * pathname.
519ff4a156dSchristos      */
520ff4a156dSchristos     LastElement = strrchr (CommonPath, '/');
521ff4a156dSchristos     if (LastElement)
522ff4a156dSchristos     {
523ff4a156dSchristos         *LastElement = 0;
524ff4a156dSchristos     }
525ff4a156dSchristos 
526ff4a156dSchristos     /* Build the final merged pathname */
527ff4a156dSchristos 
528ff4a156dSchristos ConcatenatePaths:
52925666a51Schristos     Pathname = UtLocalCacheCalloc (
53081bd9c9cSchristos         strlen (CommonPath) + strlen (FilePathname) + 2);
531ff4a156dSchristos     if (LastElement && *CommonPath)
532ff4a156dSchristos     {
533ff4a156dSchristos         strcpy (Pathname, CommonPath);
534ff4a156dSchristos         strcat (Pathname, "/");
535ff4a156dSchristos     }
536ff4a156dSchristos     strcat (Pathname, FilePathname);
537ff4a156dSchristos 
538ff4a156dSchristos     /* Convert all backslashes to normal slashes */
539ff4a156dSchristos 
540ff4a156dSchristos ConvertBackslashes:
541ff4a156dSchristos     UtConvertBackslashes (Pathname);
542ff4a156dSchristos 
543ff4a156dSchristos     DbgPrint (ASL_PARSE_OUTPUT, "Include: Merged Pathname - \"%s\"\n",
544ff4a156dSchristos          Pathname);
545ff4a156dSchristos     return (Pathname);
546ff4a156dSchristos }
547ff4a156dSchristos 
548ff4a156dSchristos 
549ff4a156dSchristos /*******************************************************************************
550ff4a156dSchristos  *
55128c506b8Sjruoho  * FUNCTION:    FlOpenIncludeWithPrefix
55228c506b8Sjruoho  *
55328c506b8Sjruoho  * PARAMETERS:  PrefixDir       - Prefix directory pathname. Can be a zero
55428c506b8Sjruoho  *                                length string.
55528c506b8Sjruoho  *              Filename        - The include filename from the source ASL.
55628c506b8Sjruoho  *
55728c506b8Sjruoho  * RETURN:      Valid file descriptor if successful. Null otherwise.
55828c506b8Sjruoho  *
55928c506b8Sjruoho  * DESCRIPTION: Open an include file and push it on the input file stack.
56028c506b8Sjruoho  *
56128c506b8Sjruoho  ******************************************************************************/
56228c506b8Sjruoho 
5639b9ee194Schristos static FILE *
56428c506b8Sjruoho FlOpenIncludeWithPrefix (
56528c506b8Sjruoho     char                    *PrefixDir,
5669b9ee194Schristos     ACPI_PARSE_OBJECT       *Op,
56728c506b8Sjruoho     char                    *Filename)
56828c506b8Sjruoho {
56928c506b8Sjruoho     FILE                    *IncludeFile;
57028c506b8Sjruoho     char                    *Pathname;
5719b9ee194Schristos     UINT32                  OriginalLineNumber;
57228c506b8Sjruoho 
57328c506b8Sjruoho 
57428c506b8Sjruoho     /* Build the full pathname to the file */
57528c506b8Sjruoho 
576ff4a156dSchristos     Pathname = FlMergePathnames (PrefixDir, Filename);
57728c506b8Sjruoho 
578ff4a156dSchristos     DbgPrint (ASL_PARSE_OUTPUT, "Include: Opening file - \"%s\"\n\n",
57928c506b8Sjruoho         Pathname);
58028c506b8Sjruoho 
58128c506b8Sjruoho     /* Attempt to open the file, push if successful */
58228c506b8Sjruoho 
58328c506b8Sjruoho     IncludeFile = fopen (Pathname, "r");
584ff4a156dSchristos     if (!IncludeFile)
58528c506b8Sjruoho     {
586ff4a156dSchristos         return (NULL);
587ff4a156dSchristos     }
588ff4a156dSchristos 
5899b9ee194Schristos     /*
5909b9ee194Schristos      * Check the entire include file for any # preprocessor directives.
5919b9ee194Schristos      * This is because there may be some confusion between the #include
5929b9ee194Schristos      * preprocessor directive and the ASL Include statement. A file included
5939b9ee194Schristos      * by the ASL include cannot contain preprocessor directives because
5949b9ee194Schristos      * the preprocessor has already run by the time the ASL include is
5959b9ee194Schristos      * recognized (by the compiler, not the preprocessor.)
5969b9ee194Schristos      *
5979b9ee194Schristos      * Note: DtGetNextLine strips/ignores comments.
5989b9ee194Schristos      * Save current line number since DtGetNextLine modifies it.
5999b9ee194Schristos      */
6007efa3256Schristos     AslGbl_CurrentLineNumber--;
6017efa3256Schristos     OriginalLineNumber = AslGbl_CurrentLineNumber;
60281bd9c9cSchristos 
6039b9ee194Schristos     while (DtGetNextLine (IncludeFile, DT_ALLOW_MULTILINE_QUOTES) != ASL_EOF)
6049b9ee194Schristos     {
6057efa3256Schristos         if (AslGbl_CurrentLineBuffer[0] == '#')
6069b9ee194Schristos         {
6079b9ee194Schristos             AslError (ASL_ERROR, ASL_MSG_INCLUDE_FILE,
6089b9ee194Schristos                 Op, "use #include instead");
6099b9ee194Schristos         }
6109b9ee194Schristos     }
61181bd9c9cSchristos 
6127efa3256Schristos     AslGbl_CurrentLineNumber = OriginalLineNumber;
6139b9ee194Schristos 
6149b9ee194Schristos     /* Must seek back to the start of the file */
6159b9ee194Schristos 
6169b9ee194Schristos     fseek (IncludeFile, 0, SEEK_SET);
6179b9ee194Schristos 
61828c506b8Sjruoho     /* Push the include file on the open input file stack */
61928c506b8Sjruoho 
62028c506b8Sjruoho     AslPushInputFileStack (IncludeFile, Pathname);
62128c506b8Sjruoho     return (IncludeFile);
62228c506b8Sjruoho }
62328c506b8Sjruoho 
62428c506b8Sjruoho 
62528c506b8Sjruoho /*******************************************************************************
62628c506b8Sjruoho  *
62728c506b8Sjruoho  * FUNCTION:    FlOpenIncludeFile
62828c506b8Sjruoho  *
62928c506b8Sjruoho  * PARAMETERS:  Op        - Parse node for the INCLUDE ASL statement
63028c506b8Sjruoho  *
63128c506b8Sjruoho  * RETURN:      None.
63228c506b8Sjruoho  *
63328c506b8Sjruoho  * DESCRIPTION: Open an include file and push it on the input file stack.
63428c506b8Sjruoho  *
63528c506b8Sjruoho  ******************************************************************************/
63628c506b8Sjruoho 
63728c506b8Sjruoho void
63828c506b8Sjruoho FlOpenIncludeFile (
63928c506b8Sjruoho     ACPI_PARSE_OBJECT       *Op)
64028c506b8Sjruoho {
64128c506b8Sjruoho     FILE                    *IncludeFile;
64228c506b8Sjruoho     ASL_INCLUDE_DIR         *NextDir;
64328c506b8Sjruoho 
64428c506b8Sjruoho 
64528c506b8Sjruoho     /* Op must be valid */
64628c506b8Sjruoho 
64728c506b8Sjruoho     if (!Op)
64828c506b8Sjruoho     {
64928c506b8Sjruoho         AslCommonError (ASL_ERROR, ASL_MSG_INCLUDE_FILE_OPEN,
6507efa3256Schristos             AslGbl_CurrentLineNumber, AslGbl_LogicalLineNumber,
6517efa3256Schristos             AslGbl_InputByteCount, AslGbl_CurrentColumn,
6527efa3256Schristos             AslGbl_Files[ASL_FILE_INPUT].Filename, " - Null parse node");
65328c506b8Sjruoho 
65428c506b8Sjruoho         return;
65528c506b8Sjruoho     }
65628c506b8Sjruoho 
65728c506b8Sjruoho     /*
65828c506b8Sjruoho      * Flush out the "include ()" statement on this line, start
65928c506b8Sjruoho      * the actual include file on the next line
66028c506b8Sjruoho      */
661ff4a156dSchristos     AslResetCurrentLineBuffer ();
66228c506b8Sjruoho     FlPrintFile (ASL_FILE_SOURCE_OUTPUT, "\n");
6637efa3256Schristos     AslGbl_CurrentLineOffset++;
66428c506b8Sjruoho 
66528c506b8Sjruoho 
66628c506b8Sjruoho     /* Attempt to open the include file */
66728c506b8Sjruoho 
66828c506b8Sjruoho     /* If the file specifies an absolute path, just open it */
66928c506b8Sjruoho 
67028c506b8Sjruoho     if ((Op->Asl.Value.String[0] == '/')  ||
67128c506b8Sjruoho         (Op->Asl.Value.String[0] == '\\') ||
67228c506b8Sjruoho         (Op->Asl.Value.String[1] == ':'))
67328c506b8Sjruoho     {
6749b9ee194Schristos         IncludeFile = FlOpenIncludeWithPrefix ("", Op, Op->Asl.Value.String);
67528c506b8Sjruoho         if (!IncludeFile)
67628c506b8Sjruoho         {
67728c506b8Sjruoho             goto ErrorExit;
67828c506b8Sjruoho         }
67928c506b8Sjruoho         return;
68028c506b8Sjruoho     }
68128c506b8Sjruoho 
68228c506b8Sjruoho     /*
68328c506b8Sjruoho      * The include filename is not an absolute path.
68428c506b8Sjruoho      *
68528c506b8Sjruoho      * First, search for the file within the "local" directory -- meaning
68628c506b8Sjruoho      * the same directory that contains the source file.
68728c506b8Sjruoho      *
68828c506b8Sjruoho      * Construct the file pathname from the global directory name.
68928c506b8Sjruoho      */
69081bd9c9cSchristos     IncludeFile = FlOpenIncludeWithPrefix (
6917efa3256Schristos         AslGbl_DirectoryPath, Op, Op->Asl.Value.String);
69228c506b8Sjruoho     if (IncludeFile)
69328c506b8Sjruoho     {
69428c506b8Sjruoho         return;
69528c506b8Sjruoho     }
69628c506b8Sjruoho 
69728c506b8Sjruoho     /*
69828c506b8Sjruoho      * Second, search for the file within the (possibly multiple) directories
69928c506b8Sjruoho      * specified by the -I option on the command line.
70028c506b8Sjruoho      */
7017efa3256Schristos     NextDir = AslGbl_IncludeDirList;
70228c506b8Sjruoho     while (NextDir)
70328c506b8Sjruoho     {
70481bd9c9cSchristos         IncludeFile = FlOpenIncludeWithPrefix (
70581bd9c9cSchristos             NextDir->Dir, Op, Op->Asl.Value.String);
70628c506b8Sjruoho         if (IncludeFile)
70728c506b8Sjruoho         {
70828c506b8Sjruoho             return;
70928c506b8Sjruoho         }
71028c506b8Sjruoho 
71128c506b8Sjruoho         NextDir = NextDir->Next;
71228c506b8Sjruoho     }
71328c506b8Sjruoho 
71428c506b8Sjruoho     /* We could not open the include file after trying very hard */
71528c506b8Sjruoho 
71628c506b8Sjruoho ErrorExit:
7177efa3256Schristos     snprintf (AslGbl_MsgBuffer, sizeof(AslGbl_MsgBuffer), "%s, %s", Op->Asl.Value.String, strerror (errno));
7187efa3256Schristos     AslError (ASL_ERROR, ASL_MSG_INCLUDE_FILE_OPEN, Op, AslGbl_MsgBuffer);
71928c506b8Sjruoho }
72028c506b8Sjruoho 
72128c506b8Sjruoho 
72228c506b8Sjruoho /*******************************************************************************
72328c506b8Sjruoho  *
72428c506b8Sjruoho  * FUNCTION:    FlOpenInputFile
72528c506b8Sjruoho  *
72628c506b8Sjruoho  * PARAMETERS:  InputFilename       - The user-specified ASL source file to be
72728c506b8Sjruoho  *                                    compiled
72828c506b8Sjruoho  *
72928c506b8Sjruoho  * RETURN:      Status
73028c506b8Sjruoho  *
73128c506b8Sjruoho  * DESCRIPTION: Open the specified input file, and save the directory path to
732a43dcd2aSchristos  *              the file so that include files can be opened in the same
733a43dcd2aSchristos  *              directory. NOTE: File is opened in text mode.
73428c506b8Sjruoho  *
73528c506b8Sjruoho  ******************************************************************************/
73628c506b8Sjruoho 
73728c506b8Sjruoho ACPI_STATUS
73828c506b8Sjruoho FlOpenInputFile (
73928c506b8Sjruoho     char                    *InputFilename)
74028c506b8Sjruoho {
74128c506b8Sjruoho 
74228c506b8Sjruoho     /* Open the input ASL file, text mode */
74328c506b8Sjruoho 
744ff4a156dSchristos     FlOpenFile (ASL_FILE_INPUT, InputFilename, "rt");
7457efa3256Schristos     AslCompilerin = AslGbl_Files[ASL_FILE_INPUT].Handle;
74628c506b8Sjruoho 
74728c506b8Sjruoho     return (AE_OK);
74828c506b8Sjruoho }
74928c506b8Sjruoho 
75028c506b8Sjruoho 
75128c506b8Sjruoho /*******************************************************************************
75228c506b8Sjruoho  *
75328c506b8Sjruoho  * FUNCTION:    FlOpenAmlOutputFile
75428c506b8Sjruoho  *
75528c506b8Sjruoho  * PARAMETERS:  FilenamePrefix       - The user-specified ASL source file
75628c506b8Sjruoho  *
75728c506b8Sjruoho  * RETURN:      Status
75828c506b8Sjruoho  *
75928c506b8Sjruoho  * DESCRIPTION: Create the output filename (*.AML) and open the file. The file
76028c506b8Sjruoho  *              is created in the same directory as the parent input file.
76128c506b8Sjruoho  *
76228c506b8Sjruoho  ******************************************************************************/
76328c506b8Sjruoho 
76428c506b8Sjruoho ACPI_STATUS
76528c506b8Sjruoho FlOpenAmlOutputFile (
76628c506b8Sjruoho     char                    *FilenamePrefix)
76728c506b8Sjruoho {
76828c506b8Sjruoho     char                    *Filename;
76928c506b8Sjruoho 
77028c506b8Sjruoho 
77128c506b8Sjruoho     /* Output filename usually comes from the ASL itself */
77228c506b8Sjruoho 
7737efa3256Schristos     Filename = AslGbl_Files[ASL_FILE_AML_OUTPUT].Filename;
77428c506b8Sjruoho     if (!Filename)
77528c506b8Sjruoho     {
77628c506b8Sjruoho         /* Create the output AML filename */
777f45f09e8Schristos         if (!AcpiGbl_CaptureComments)
7788f1e17bdSchristos         {
77928c506b8Sjruoho             Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_AML_CODE);
7808f1e17bdSchristos         }
7818f1e17bdSchristos         else
7828f1e17bdSchristos         {
7838f1e17bdSchristos             Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_CONVERT_AML);
7848f1e17bdSchristos         }
78528c506b8Sjruoho         if (!Filename)
78628c506b8Sjruoho         {
78728c506b8Sjruoho             AslCommonError (ASL_ERROR, ASL_MSG_OUTPUT_FILENAME,
78828c506b8Sjruoho                 0, 0, 0, 0, NULL, NULL);
78928c506b8Sjruoho             return (AE_ERROR);
79028c506b8Sjruoho         }
791cb2bd8f0Schristos 
7927efa3256Schristos         AslGbl_Files[ASL_FILE_AML_OUTPUT].Filename = Filename;
79328c506b8Sjruoho     }
79428c506b8Sjruoho 
79528c506b8Sjruoho     /* Open the output AML file in binary mode */
79628c506b8Sjruoho 
79728c506b8Sjruoho     FlOpenFile (ASL_FILE_AML_OUTPUT, Filename, "w+b");
79828c506b8Sjruoho     return (AE_OK);
79928c506b8Sjruoho }
80028c506b8Sjruoho 
80128c506b8Sjruoho 
80228c506b8Sjruoho /*******************************************************************************
80328c506b8Sjruoho  *
80428c506b8Sjruoho  * FUNCTION:    FlOpenMiscOutputFiles
80528c506b8Sjruoho  *
80628c506b8Sjruoho  * PARAMETERS:  FilenamePrefix       - The user-specified ASL source file
80728c506b8Sjruoho  *
80828c506b8Sjruoho  * RETURN:      Status
80928c506b8Sjruoho  *
81028c506b8Sjruoho  * DESCRIPTION: Create and open the various output files needed, depending on
81128c506b8Sjruoho  *              the command line options
81228c506b8Sjruoho  *
81328c506b8Sjruoho  ******************************************************************************/
81428c506b8Sjruoho 
81528c506b8Sjruoho ACPI_STATUS
81628c506b8Sjruoho FlOpenMiscOutputFiles (
81728c506b8Sjruoho     char                    *FilenamePrefix)
81828c506b8Sjruoho {
81928c506b8Sjruoho     char                    *Filename;
82028c506b8Sjruoho 
82128c506b8Sjruoho 
8229b9ee194Schristos      /* Create/Open a map file if requested */
8239b9ee194Schristos 
8247efa3256Schristos     if (AslGbl_MapfileFlag)
8259b9ee194Schristos     {
8269b9ee194Schristos         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_MAP);
8279b9ee194Schristos         if (!Filename)
8289b9ee194Schristos         {
8299b9ee194Schristos             AslCommonError (ASL_ERROR, ASL_MSG_LISTING_FILENAME,
8309b9ee194Schristos                 0, 0, 0, 0, NULL, NULL);
8319b9ee194Schristos             return (AE_ERROR);
8329b9ee194Schristos         }
8339b9ee194Schristos 
8349b9ee194Schristos         /* Open the hex file, text mode (closed at compiler exit) */
8359b9ee194Schristos 
8369b9ee194Schristos         FlOpenFile (ASL_FILE_MAP_OUTPUT, Filename, "w+t");
8379b9ee194Schristos 
8389b9ee194Schristos         AslCompilerSignon (ASL_FILE_MAP_OUTPUT);
8399b9ee194Schristos         AslCompilerFileHeader (ASL_FILE_MAP_OUTPUT);
8409b9ee194Schristos     }
8419b9ee194Schristos 
842ff4a156dSchristos     /* All done for disassembler */
843ff4a156dSchristos 
8447efa3256Schristos     if (AslGbl_FileType == ASL_INPUT_TYPE_BINARY_ACPI_TABLE)
845ff4a156dSchristos     {
846ff4a156dSchristos         return (AE_OK);
847ff4a156dSchristos     }
848ff4a156dSchristos 
849124f4c82Sjruoho     /* Create/Open a hex output file if asked */
85028c506b8Sjruoho 
8517efa3256Schristos     if (AslGbl_HexOutputFlag)
852124f4c82Sjruoho     {
853124f4c82Sjruoho         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_HEX_DUMP);
85428c506b8Sjruoho         if (!Filename)
85528c506b8Sjruoho         {
85628c506b8Sjruoho             AslCommonError (ASL_ERROR, ASL_MSG_LISTING_FILENAME,
85728c506b8Sjruoho                 0, 0, 0, 0, NULL, NULL);
85828c506b8Sjruoho             return (AE_ERROR);
85928c506b8Sjruoho         }
86028c506b8Sjruoho 
861124f4c82Sjruoho         /* Open the hex file, text mode */
862124f4c82Sjruoho 
863ff4a156dSchristos         FlOpenFile (ASL_FILE_HEX_OUTPUT, Filename, "w+t");
864124f4c82Sjruoho 
865124f4c82Sjruoho         AslCompilerSignon (ASL_FILE_HEX_OUTPUT);
866124f4c82Sjruoho         AslCompilerFileHeader (ASL_FILE_HEX_OUTPUT);
867124f4c82Sjruoho     }
868124f4c82Sjruoho 
869124f4c82Sjruoho     /* Create/Open a debug output file if asked */
870124f4c82Sjruoho 
8717efa3256Schristos     if (AslGbl_DebugFlag)
872124f4c82Sjruoho     {
873124f4c82Sjruoho         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_DEBUG);
874124f4c82Sjruoho         if (!Filename)
875124f4c82Sjruoho         {
876124f4c82Sjruoho             AslCommonError (ASL_ERROR, ASL_MSG_DEBUG_FILENAME,
877124f4c82Sjruoho                 0, 0, 0, 0, NULL, NULL);
878124f4c82Sjruoho             return (AE_ERROR);
879124f4c82Sjruoho         }
880124f4c82Sjruoho 
881124f4c82Sjruoho         /* Open the debug file as STDERR, text mode */
882124f4c82Sjruoho 
8837efa3256Schristos         AslGbl_Files[ASL_FILE_DEBUG_OUTPUT].Filename = Filename;
8847efa3256Schristos         AslGbl_Files[ASL_FILE_DEBUG_OUTPUT].Handle =
885124f4c82Sjruoho             freopen (Filename, "w+t", stderr);
886124f4c82Sjruoho 
8877efa3256Schristos         if (!AslGbl_Files[ASL_FILE_DEBUG_OUTPUT].Handle)
888ff4a156dSchristos         {
889cb2bd8f0Schristos             /*
8909b9ee194Schristos              * A problem with freopen is that on error, we no longer
8919b9ee194Schristos              * have stderr and cannot emit normal error messages.
8929b9ee194Schristos              * Emit error to stdout, close files, and exit.
893cb2bd8f0Schristos              */
8949b9ee194Schristos             fprintf (stdout,
8959b9ee194Schristos                 "\nCould not open debug output file: %s\n\n", Filename);
8969b9ee194Schristos 
8979b9ee194Schristos             CmCleanupAndExit ();
8989b9ee194Schristos             exit (1);
899ff4a156dSchristos         }
900ff4a156dSchristos 
901124f4c82Sjruoho         AslCompilerSignon (ASL_FILE_DEBUG_OUTPUT);
902124f4c82Sjruoho         AslCompilerFileHeader (ASL_FILE_DEBUG_OUTPUT);
903124f4c82Sjruoho     }
90428c506b8Sjruoho 
90549c2f1f4Schristos     /* Create/Open a cross-reference output file if asked */
90649c2f1f4Schristos 
9077efa3256Schristos     if (AslGbl_CrossReferenceOutput)
90849c2f1f4Schristos     {
90949c2f1f4Schristos         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_XREF);
91049c2f1f4Schristos         if (!Filename)
91149c2f1f4Schristos         {
91249c2f1f4Schristos             AslCommonError (ASL_ERROR, ASL_MSG_DEBUG_FILENAME,
91349c2f1f4Schristos                 0, 0, 0, 0, NULL, NULL);
91449c2f1f4Schristos             return (AE_ERROR);
91549c2f1f4Schristos         }
91649c2f1f4Schristos 
91749c2f1f4Schristos         FlOpenFile (ASL_FILE_XREF_OUTPUT, Filename, "w+t");
91849c2f1f4Schristos 
91949c2f1f4Schristos         AslCompilerSignon (ASL_FILE_XREF_OUTPUT);
92049c2f1f4Schristos         AslCompilerFileHeader (ASL_FILE_XREF_OUTPUT);
92149c2f1f4Schristos     }
92249c2f1f4Schristos 
92328c506b8Sjruoho     /* Create/Open a listing output file if asked */
92428c506b8Sjruoho 
9257efa3256Schristos     if (AslGbl_ListingFlag)
92628c506b8Sjruoho     {
92728c506b8Sjruoho         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_LISTING);
92828c506b8Sjruoho         if (!Filename)
92928c506b8Sjruoho         {
93028c506b8Sjruoho             AslCommonError (ASL_ERROR, ASL_MSG_LISTING_FILENAME,
93128c506b8Sjruoho                 0, 0, 0, 0, NULL, NULL);
93228c506b8Sjruoho             return (AE_ERROR);
93328c506b8Sjruoho         }
93428c506b8Sjruoho 
93528c506b8Sjruoho         /* Open the listing file, text mode */
93628c506b8Sjruoho 
937ff4a156dSchristos         FlOpenFile (ASL_FILE_LISTING_OUTPUT, Filename, "w+t");
93828c506b8Sjruoho 
93928c506b8Sjruoho         AslCompilerSignon (ASL_FILE_LISTING_OUTPUT);
94028c506b8Sjruoho         AslCompilerFileHeader (ASL_FILE_LISTING_OUTPUT);
94128c506b8Sjruoho     }
94228c506b8Sjruoho 
9439b9ee194Schristos     /* Create the preprocessor output temp file if preprocessor enabled */
944ff4a156dSchristos 
9457efa3256Schristos     if (AslGbl_PreprocessFlag)
946ff4a156dSchristos     {
947ff4a156dSchristos         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_PREPROCESSOR);
948ff4a156dSchristos         if (!Filename)
949ff4a156dSchristos         {
950ff4a156dSchristos             AslCommonError (ASL_ERROR, ASL_MSG_PREPROCESSOR_FILENAME,
951ff4a156dSchristos                 0, 0, 0, 0, NULL, NULL);
952ff4a156dSchristos             return (AE_ERROR);
953ff4a156dSchristos         }
954ff4a156dSchristos 
955ff4a156dSchristos         FlOpenFile (ASL_FILE_PREPROCESSOR, Filename, "w+t");
956ff4a156dSchristos     }
957ff4a156dSchristos 
9589b9ee194Schristos     /*
9599b9ee194Schristos      * Create the "user" preprocessor output file if -li flag set.
9609b9ee194Schristos      * Note, this file contains no embedded #line directives.
9619b9ee194Schristos      */
9627efa3256Schristos     if (AslGbl_PreprocessorOutputFlag)
9639b9ee194Schristos     {
9649b9ee194Schristos         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_PREPROC_USER);
9659b9ee194Schristos         if (!Filename)
9669b9ee194Schristos         {
9679b9ee194Schristos             AslCommonError (ASL_ERROR, ASL_MSG_PREPROCESSOR_FILENAME,
9689b9ee194Schristos                 0, 0, 0, 0, NULL, NULL);
9699b9ee194Schristos             return (AE_ERROR);
9709b9ee194Schristos         }
9719b9ee194Schristos 
9729b9ee194Schristos         FlOpenFile (ASL_FILE_PREPROCESSOR_USER, Filename, "w+t");
9739b9ee194Schristos     }
9749b9ee194Schristos 
975ff4a156dSchristos     /* All done for data table compiler */
976ff4a156dSchristos 
9777efa3256Schristos     if (AslGbl_FileType == ASL_INPUT_TYPE_ASCII_DATA)
978124f4c82Sjruoho     {
979124f4c82Sjruoho         return (AE_OK);
980124f4c82Sjruoho     }
981124f4c82Sjruoho 
982124f4c82Sjruoho     /* Create/Open a combined source output file */
983124f4c82Sjruoho 
984124f4c82Sjruoho     Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_SOURCE);
985124f4c82Sjruoho     if (!Filename)
986124f4c82Sjruoho     {
987124f4c82Sjruoho         AslCommonError (ASL_ERROR, ASL_MSG_LISTING_FILENAME,
988124f4c82Sjruoho             0, 0, 0, 0, NULL, NULL);
989124f4c82Sjruoho         return (AE_ERROR);
990124f4c82Sjruoho     }
991124f4c82Sjruoho 
992124f4c82Sjruoho     /*
993124f4c82Sjruoho      * Open the source output file, binary mode (so that LF does not get
994124f4c82Sjruoho      * expanded to CR/LF on some systems, messing up our seek
995124f4c82Sjruoho      * calculations.)
996124f4c82Sjruoho      */
997124f4c82Sjruoho     FlOpenFile (ASL_FILE_SOURCE_OUTPUT, Filename, "w+b");
998124f4c82Sjruoho 
999ff4a156dSchristos /*
1000ff4a156dSchristos // TBD: TEMP
10017efa3256Schristos //    AslCompilerin = AslGbl_Files[ASL_FILE_SOURCE_OUTPUT].Handle;
1002ff4a156dSchristos */
100328c506b8Sjruoho     /* Create/Open a assembly code source output file if asked */
100428c506b8Sjruoho 
10057efa3256Schristos     if (AslGbl_AsmOutputFlag)
100628c506b8Sjruoho     {
100728c506b8Sjruoho         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_ASM_SOURCE);
100828c506b8Sjruoho         if (!Filename)
100928c506b8Sjruoho         {
101028c506b8Sjruoho             AslCommonError (ASL_ERROR, ASL_MSG_LISTING_FILENAME,
101128c506b8Sjruoho                 0, 0, 0, 0, NULL, NULL);
101228c506b8Sjruoho             return (AE_ERROR);
101328c506b8Sjruoho         }
101428c506b8Sjruoho 
101528c506b8Sjruoho         /* Open the assembly code source file, text mode */
101628c506b8Sjruoho 
1017ff4a156dSchristos         FlOpenFile (ASL_FILE_ASM_SOURCE_OUTPUT, Filename, "w+t");
101828c506b8Sjruoho 
101928c506b8Sjruoho         AslCompilerSignon (ASL_FILE_ASM_SOURCE_OUTPUT);
102028c506b8Sjruoho         AslCompilerFileHeader (ASL_FILE_ASM_SOURCE_OUTPUT);
102128c506b8Sjruoho     }
102228c506b8Sjruoho 
102328c506b8Sjruoho     /* Create/Open a C code source output file if asked */
102428c506b8Sjruoho 
10257efa3256Schristos     if (AslGbl_C_OutputFlag)
102628c506b8Sjruoho     {
102728c506b8Sjruoho         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_C_SOURCE);
102828c506b8Sjruoho         if (!Filename)
102928c506b8Sjruoho         {
103028c506b8Sjruoho             AslCommonError (ASL_ERROR, ASL_MSG_LISTING_FILENAME,
103128c506b8Sjruoho                 0, 0, 0, 0, NULL, NULL);
103228c506b8Sjruoho             return (AE_ERROR);
103328c506b8Sjruoho         }
103428c506b8Sjruoho 
103528c506b8Sjruoho         /* Open the C code source file, text mode */
103628c506b8Sjruoho 
1037ff4a156dSchristos         FlOpenFile (ASL_FILE_C_SOURCE_OUTPUT, Filename, "w+t");
103828c506b8Sjruoho 
103928c506b8Sjruoho         FlPrintFile (ASL_FILE_C_SOURCE_OUTPUT, "/*\n");
104028c506b8Sjruoho         AslCompilerSignon (ASL_FILE_C_SOURCE_OUTPUT);
104128c506b8Sjruoho         AslCompilerFileHeader (ASL_FILE_C_SOURCE_OUTPUT);
104228c506b8Sjruoho     }
104328c506b8Sjruoho 
1044ff4a156dSchristos     /* Create/Open a C code source output file for the offset table if asked */
1045ff4a156dSchristos 
10467efa3256Schristos     if (AslGbl_C_OffsetTableFlag)
1047ff4a156dSchristos     {
1048ff4a156dSchristos         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_C_OFFSET);
1049ff4a156dSchristos         if (!Filename)
1050ff4a156dSchristos         {
1051ff4a156dSchristos             AslCommonError (ASL_ERROR, ASL_MSG_LISTING_FILENAME,
1052ff4a156dSchristos                 0, 0, 0, 0, NULL, NULL);
1053ff4a156dSchristos             return (AE_ERROR);
1054ff4a156dSchristos         }
1055ff4a156dSchristos 
1056ff4a156dSchristos         /* Open the C code source file, text mode */
1057ff4a156dSchristos 
1058ff4a156dSchristos         FlOpenFile (ASL_FILE_C_OFFSET_OUTPUT, Filename, "w+t");
1059ff4a156dSchristos 
1060ff4a156dSchristos         FlPrintFile (ASL_FILE_C_OFFSET_OUTPUT, "/*\n");
1061ff4a156dSchristos         AslCompilerSignon (ASL_FILE_C_OFFSET_OUTPUT);
1062ff4a156dSchristos         AslCompilerFileHeader (ASL_FILE_C_OFFSET_OUTPUT);
1063ff4a156dSchristos     }
1064ff4a156dSchristos 
106528c506b8Sjruoho     /* Create/Open a assembly include output file if asked */
106628c506b8Sjruoho 
10677efa3256Schristos     if (AslGbl_AsmIncludeOutputFlag)
106828c506b8Sjruoho     {
106928c506b8Sjruoho         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_ASM_INCLUDE);
107028c506b8Sjruoho         if (!Filename)
107128c506b8Sjruoho         {
107228c506b8Sjruoho             AslCommonError (ASL_ERROR, ASL_MSG_LISTING_FILENAME,
107328c506b8Sjruoho                 0, 0, 0, 0, NULL, NULL);
107428c506b8Sjruoho             return (AE_ERROR);
107528c506b8Sjruoho         }
107628c506b8Sjruoho 
107728c506b8Sjruoho         /* Open the assembly include file, text mode */
107828c506b8Sjruoho 
1079ff4a156dSchristos         FlOpenFile (ASL_FILE_ASM_INCLUDE_OUTPUT, Filename, "w+t");
108028c506b8Sjruoho 
108128c506b8Sjruoho         AslCompilerSignon (ASL_FILE_ASM_INCLUDE_OUTPUT);
108228c506b8Sjruoho         AslCompilerFileHeader (ASL_FILE_ASM_INCLUDE_OUTPUT);
108328c506b8Sjruoho     }
108428c506b8Sjruoho 
108528c506b8Sjruoho     /* Create/Open a C include output file if asked */
108628c506b8Sjruoho 
10877efa3256Schristos     if (AslGbl_C_IncludeOutputFlag)
108828c506b8Sjruoho     {
108928c506b8Sjruoho         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_C_INCLUDE);
109028c506b8Sjruoho         if (!Filename)
109128c506b8Sjruoho         {
109228c506b8Sjruoho             AslCommonError (ASL_ERROR, ASL_MSG_LISTING_FILENAME,
109328c506b8Sjruoho                 0, 0, 0, 0, NULL, NULL);
109428c506b8Sjruoho             return (AE_ERROR);
109528c506b8Sjruoho         }
109628c506b8Sjruoho 
109728c506b8Sjruoho         /* Open the C include file, text mode */
109828c506b8Sjruoho 
1099ff4a156dSchristos         FlOpenFile (ASL_FILE_C_INCLUDE_OUTPUT, Filename, "w+t");
110028c506b8Sjruoho 
110128c506b8Sjruoho         FlPrintFile (ASL_FILE_C_INCLUDE_OUTPUT, "/*\n");
110228c506b8Sjruoho         AslCompilerSignon (ASL_FILE_C_INCLUDE_OUTPUT);
110328c506b8Sjruoho         AslCompilerFileHeader (ASL_FILE_C_INCLUDE_OUTPUT);
110428c506b8Sjruoho     }
110528c506b8Sjruoho 
110628c506b8Sjruoho     /* Create a namespace output file if asked */
110728c506b8Sjruoho 
11087efa3256Schristos     if (AslGbl_NsOutputFlag)
110928c506b8Sjruoho     {
111028c506b8Sjruoho         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_NAMESPACE);
111128c506b8Sjruoho         if (!Filename)
111228c506b8Sjruoho         {
111328c506b8Sjruoho             AslCommonError (ASL_ERROR, ASL_MSG_LISTING_FILENAME,
111428c506b8Sjruoho                 0, 0, 0, 0, NULL, NULL);
111528c506b8Sjruoho             return (AE_ERROR);
111628c506b8Sjruoho         }
111728c506b8Sjruoho 
111828c506b8Sjruoho         /* Open the namespace file, text mode */
111928c506b8Sjruoho 
1120ff4a156dSchristos         FlOpenFile (ASL_FILE_NAMESPACE_OUTPUT, Filename, "w+t");
112128c506b8Sjruoho 
112228c506b8Sjruoho         AslCompilerSignon (ASL_FILE_NAMESPACE_OUTPUT);
112328c506b8Sjruoho         AslCompilerFileHeader (ASL_FILE_NAMESPACE_OUTPUT);
112428c506b8Sjruoho     }
112528c506b8Sjruoho 
11268f1e17bdSchristos     /* Create a debug file for the converter */
11278f1e17bdSchristos 
11288f1e17bdSchristos     if (AcpiGbl_DebugAslConversion)
11298f1e17bdSchristos     {
11308f1e17bdSchristos         Filename = FlGenerateFilename (FilenamePrefix, FILE_SUFFIX_CONVERT_DEBUG);
11318f1e17bdSchristos         if (!Filename)
11328f1e17bdSchristos         {
11338f1e17bdSchristos             AslCommonError (ASL_ERROR, ASL_MSG_LISTING_FILENAME,
11348f1e17bdSchristos                 0, 0, 0, 0, NULL, NULL);
11358f1e17bdSchristos             return (AE_ERROR);
11368f1e17bdSchristos         }
11378f1e17bdSchristos 
11388f1e17bdSchristos         /* Open the converter debug file, text mode */
11398f1e17bdSchristos 
11408f1e17bdSchristos         FlOpenFile (ASL_FILE_CONV_DEBUG_OUTPUT, Filename, "w+t");
11418f1e17bdSchristos 
11428f1e17bdSchristos         AslCompilerSignon (ASL_FILE_CONV_DEBUG_OUTPUT);
11438f1e17bdSchristos         AslCompilerFileHeader (ASL_FILE_CONV_DEBUG_OUTPUT);
11448f1e17bdSchristos 
11457efa3256Schristos         AcpiGbl_ConvDebugFile = AslGbl_Files[ASL_FILE_CONV_DEBUG_OUTPUT].Handle;
11468f1e17bdSchristos     }
11478f1e17bdSchristos 
114828c506b8Sjruoho     return (AE_OK);
114928c506b8Sjruoho }
115028c506b8Sjruoho 
115128c506b8Sjruoho 
115228c506b8Sjruoho #ifdef ACPI_OBSOLETE_FUNCTIONS
115328c506b8Sjruoho /*******************************************************************************
115428c506b8Sjruoho  *
115528c506b8Sjruoho  * FUNCTION:    FlParseInputPathname
115628c506b8Sjruoho  *
115728c506b8Sjruoho  * PARAMETERS:  InputFilename       - The user-specified ASL source file to be
115828c506b8Sjruoho  *                                    compiled
115928c506b8Sjruoho  *
116028c506b8Sjruoho  * RETURN:      Status
116128c506b8Sjruoho  *
116228c506b8Sjruoho  * DESCRIPTION: Split the input path into a directory and filename part
116328c506b8Sjruoho  *              1) Directory part used to open include files
116428c506b8Sjruoho  *              2) Filename part used to generate output filenames
116528c506b8Sjruoho  *
116628c506b8Sjruoho  ******************************************************************************/
116728c506b8Sjruoho 
116828c506b8Sjruoho ACPI_STATUS
116928c506b8Sjruoho FlParseInputPathname (
117028c506b8Sjruoho     char                    *InputFilename)
117128c506b8Sjruoho {
117228c506b8Sjruoho     char                    *Substring;
117328c506b8Sjruoho 
117428c506b8Sjruoho 
117528c506b8Sjruoho     if (!InputFilename)
117628c506b8Sjruoho     {
117728c506b8Sjruoho         return (AE_OK);
117828c506b8Sjruoho     }
117928c506b8Sjruoho 
118028c506b8Sjruoho     /* Get the path to the input filename's directory */
118128c506b8Sjruoho 
11827efa3256Schristos     AslGbl_DirectoryPath = strdup (InputFilename);
11837efa3256Schristos     if (!AslGbl_DirectoryPath)
118428c506b8Sjruoho     {
118528c506b8Sjruoho         return (AE_NO_MEMORY);
118628c506b8Sjruoho     }
118728c506b8Sjruoho 
11887efa3256Schristos     Substring = strrchr (AslGbl_DirectoryPath, '\\');
118928c506b8Sjruoho     if (!Substring)
119028c506b8Sjruoho     {
11917efa3256Schristos         Substring = strrchr (AslGbl_DirectoryPath, '/');
119228c506b8Sjruoho         if (!Substring)
119328c506b8Sjruoho         {
11947efa3256Schristos             Substring = strrchr (AslGbl_DirectoryPath, ':');
119528c506b8Sjruoho         }
119628c506b8Sjruoho     }
119728c506b8Sjruoho 
119828c506b8Sjruoho     if (!Substring)
119928c506b8Sjruoho     {
12007efa3256Schristos         AslGbl_DirectoryPath[0] = 0;
12017efa3256Schristos         if (AslGbl_UseDefaultAmlFilename)
120228c506b8Sjruoho         {
12037efa3256Schristos             AslGbl_OutputFilenamePrefix = strdup (InputFilename);
120428c506b8Sjruoho         }
120528c506b8Sjruoho     }
120628c506b8Sjruoho     else
120728c506b8Sjruoho     {
12087efa3256Schristos         if (AslGbl_UseDefaultAmlFilename)
120928c506b8Sjruoho         {
12107efa3256Schristos             AslGbl_OutputFilenamePrefix = strdup (Substring + 1);
121128c506b8Sjruoho         }
121228c506b8Sjruoho         *(Substring+1) = 0;
121328c506b8Sjruoho     }
121428c506b8Sjruoho 
12157efa3256Schristos     UtConvertBackslashes (AslGbl_OutputFilenamePrefix);
121628c506b8Sjruoho     return (AE_OK);
121728c506b8Sjruoho }
121828c506b8Sjruoho #endif
1219