]> rtime.felk.cvut.cz Git - l4.git/blob - l4/pkg/acpica/lib-acpi/src/acpica/tools/acpisrc/asfile.c
Some minor fixes.
[l4.git] / l4 / pkg / acpica / lib-acpi / src / acpica / tools / acpisrc / asfile.c
1 /******************************************************************************
2  *
3  * Module Name: asfile - Main module for the acpi source processor utility
4  *
5  *****************************************************************************/
6
7 /******************************************************************************
8  *
9  * 1. Copyright Notice
10  *
11  * Some or all of this work - Copyright (c) 1999 - 2012, Intel Corp.
12  * All rights reserved.
13  *
14  * 2. License
15  *
16  * 2.1. This is your license from Intel Corp. under its intellectual property
17  * rights. You may have additional license terms from the party that provided
18  * you this software, covering your right to use that party's intellectual
19  * property rights.
20  *
21  * 2.2. Intel grants, free of charge, to any person ("Licensee") obtaining a
22  * copy of the source code appearing in this file ("Covered Code") an
23  * irrevocable, perpetual, worldwide license under Intel's copyrights in the
24  * base code distributed originally by Intel ("Original Intel Code") to copy,
25  * make derivatives, distribute, use and display any portion of the Covered
26  * Code in any form, with the right to sublicense such rights; and
27  *
28  * 2.3. Intel grants Licensee a non-exclusive and non-transferable patent
29  * license (with the right to sublicense), under only those claims of Intel
30  * patents that are infringed by the Original Intel Code, to make, use, sell,
31  * offer to sell, and import the Covered Code and derivative works thereof
32  * solely to the minimum extent necessary to exercise the above copyright
33  * license, and in no event shall the patent license extend to any additions
34  * to or modifications of the Original Intel Code. No other license or right
35  * is granted directly or by implication, estoppel or otherwise;
36  *
37  * The above copyright and patent license is granted only if the following
38  * conditions are met:
39  *
40  * 3. Conditions
41  *
42  * 3.1. Redistribution of Source with Rights to Further Distribute Source.
43  * Redistribution of source code of any substantial portion of the Covered
44  * Code or modification with rights to further distribute source must include
45  * the above Copyright Notice, the above License, this list of Conditions,
46  * and the following Disclaimer and Export Compliance provision. In addition,
47  * Licensee must cause all Covered Code to which Licensee contributes to
48  * contain a file documenting the changes Licensee made to create that Covered
49  * Code and the date of any change. Licensee must include in that file the
50  * documentation of any changes made by any predecessor Licensee. Licensee
51  * must include a prominent statement that the modification is derived,
52  * directly or indirectly, from Original Intel Code.
53  *
54  * 3.2. Redistribution of Source with no Rights to Further Distribute Source.
55  * Redistribution of source code of any substantial portion of the Covered
56  * Code or modification without rights to further distribute source must
57  * include the following Disclaimer and Export Compliance provision in the
58  * documentation and/or other materials provided with distribution. In
59  * addition, Licensee may not authorize further sublicense of source of any
60  * portion of the Covered Code, and must include terms to the effect that the
61  * license from Licensee to its licensee is limited to the intellectual
62  * property embodied in the software Licensee provides to its licensee, and
63  * not to intellectual property embodied in modifications its licensee may
64  * make.
65  *
66  * 3.3. Redistribution of Executable. Redistribution in executable form of any
67  * substantial portion of the Covered Code or modification must reproduce the
68  * above Copyright Notice, and the following Disclaimer and Export Compliance
69  * provision in the documentation and/or other materials provided with the
70  * distribution.
71  *
72  * 3.4. Intel retains all right, title, and interest in and to the Original
73  * Intel Code.
74  *
75  * 3.5. Neither the name Intel nor any other trademark owned or controlled by
76  * Intel shall be used in advertising or otherwise to promote the sale, use or
77  * other dealings in products derived from or relating to the Covered Code
78  * without prior written authorization from Intel.
79  *
80  * 4. Disclaimer and Export Compliance
81  *
82  * 4.1. INTEL MAKES NO WARRANTY OF ANY KIND REGARDING ANY SOFTWARE PROVIDED
83  * HERE. ANY SOFTWARE ORIGINATING FROM INTEL OR DERIVED FROM INTEL SOFTWARE
84  * IS PROVIDED "AS IS," AND INTEL WILL NOT PROVIDE ANY SUPPORT, ASSISTANCE,
85  * INSTALLATION, TRAINING OR OTHER SERVICES. INTEL WILL NOT PROVIDE ANY
86  * UPDATES, ENHANCEMENTS OR EXTENSIONS. INTEL SPECIFICALLY DISCLAIMS ANY
87  * IMPLIED WARRANTIES OF MERCHANTABILITY, NONINFRINGEMENT AND FITNESS FOR A
88  * PARTICULAR PURPOSE.
89  *
90  * 4.2. IN NO EVENT SHALL INTEL HAVE ANY LIABILITY TO LICENSEE, ITS LICENSEES
91  * OR ANY OTHER THIRD PARTY, FOR ANY LOST PROFITS, LOST DATA, LOSS OF USE OR
92  * COSTS OF PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, OR FOR ANY INDIRECT,
93  * SPECIAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THIS AGREEMENT, UNDER ANY
94  * CAUSE OF ACTION OR THEORY OF LIABILITY, AND IRRESPECTIVE OF WHETHER INTEL
95  * HAS ADVANCE NOTICE OF THE POSSIBILITY OF SUCH DAMAGES. THESE LIMITATIONS
96  * SHALL APPLY NOTWITHSTANDING THE FAILURE OF THE ESSENTIAL PURPOSE OF ANY
97  * LIMITED REMEDY.
98  *
99  * 4.3. Licensee shall not export, either directly or indirectly, any of this
100  * software or system incorporating such software without first obtaining any
101  * required license or other approval from the U. S. Department of Commerce or
102  * any other agency or department of the United States Government. In the
103  * event Licensee exports any such software from the United States or
104  * re-exports any such software from a foreign destination, Licensee shall
105  * ensure that the distribution and export/re-export of the software is in
106  * compliance with all laws, regulations, orders, or other restrictions of the
107  * U.S. Export Administration Regulations. Licensee agrees that neither it nor
108  * any of its subsidiaries will export/re-export any technical data, process,
109  * software, or service, directly or indirectly, to any country for which the
110  * United States government or any agency thereof requires an export license,
111  * other governmental approval, or letter of assurance, without first obtaining
112  * such license, approval or letter.
113  *
114  *****************************************************************************/
115
116 #include "acpisrc.h"
117
118 /* Local prototypes */
119
120 void
121 AsDoWildcard (
122     ACPI_CONVERSION_TABLE   *ConversionTable,
123     char                    *SourcePath,
124     char                    *TargetPath,
125     int                     MaxPathLength,
126     int                     FileType,
127     char                    *WildcardSpec);
128
129 BOOLEAN
130 AsDetectLoneLineFeeds (
131     char                    *Filename,
132     char                    *Buffer);
133
134 static ACPI_INLINE int
135 AsMaxInt (int a, int b)
136 {
137     return (a > b ? a : b);
138 }
139
140
141 /******************************************************************************
142  *
143  * FUNCTION:    AsDoWildcard
144  *
145  * DESCRIPTION: Process files via wildcards
146  *
147  ******************************************************************************/
148
149 void
150 AsDoWildcard (
151     ACPI_CONVERSION_TABLE   *ConversionTable,
152     char                    *SourcePath,
153     char                    *TargetPath,
154     int                     MaxPathLength,
155     int                     FileType,
156     char                    *WildcardSpec)
157 {
158     void                    *DirInfo;
159     char                    *Filename;
160     char                    *SourceDirPath;
161     char                    *TargetDirPath;
162     char                    RequestedFileType;
163
164
165     if (FileType == FILE_TYPE_DIRECTORY)
166     {
167         RequestedFileType = REQUEST_DIR_ONLY;
168     }
169     else
170     {
171         RequestedFileType = REQUEST_FILE_ONLY;
172     }
173
174     VERBOSE_PRINT (("Checking for %s source files in directory \"%s\"\n",
175             WildcardSpec, SourcePath));
176
177     /* Open the directory for wildcard search */
178
179     DirInfo = AcpiOsOpenDirectory (SourcePath, WildcardSpec, RequestedFileType);
180     if (DirInfo)
181     {
182         /*
183          * Get all of the files that match both the
184          * wildcard and the requested file type
185          */
186         while ((Filename = AcpiOsGetNextFilename (DirInfo)))
187         {
188             /* Looking for directory files, must check file type */
189
190             switch (RequestedFileType)
191             {
192             case REQUEST_DIR_ONLY:
193
194                 /* If we actually have a dir, process the subtree */
195
196                 if (!AsCheckForDirectory (SourcePath, TargetPath, Filename,
197                         &SourceDirPath, &TargetDirPath))
198                 {
199                     VERBOSE_PRINT (("Subdirectory: %s\n", Filename));
200
201                     AsProcessTree (ConversionTable, SourceDirPath, TargetDirPath);
202                     free (SourceDirPath);
203                     free (TargetDirPath);
204                 }
205                 break;
206
207             case REQUEST_FILE_ONLY:
208
209                 /* Otherwise, this is a file, not a directory */
210
211                 VERBOSE_PRINT (("File: %s\n", Filename));
212
213                 AsProcessOneFile (ConversionTable, SourcePath, TargetPath,
214                         MaxPathLength, Filename, FileType);
215                 break;
216
217             default:
218                 break;
219             }
220         }
221
222         /* Cleanup */
223
224         AcpiOsCloseDirectory (DirInfo);
225     }
226 }
227
228
229 /******************************************************************************
230  *
231  * FUNCTION:    AsProcessTree
232  *
233  * DESCRIPTION: Process the directory tree. Files with the extension ".C" and
234  *              ".H" are processed as the tree is traversed.
235  *
236  ******************************************************************************/
237
238 ACPI_NATIVE_INT
239 AsProcessTree (
240     ACPI_CONVERSION_TABLE   *ConversionTable,
241     char                    *SourcePath,
242     char                    *TargetPath)
243 {
244     int                     MaxPathLength;
245
246
247     MaxPathLength = AsMaxInt (strlen (SourcePath), strlen (TargetPath));
248
249     if (!(ConversionTable->Flags & FLG_NO_FILE_OUTPUT))
250     {
251         if (ConversionTable->Flags & FLG_LOWERCASE_DIRNAMES)
252         {
253             strlwr (TargetPath);
254         }
255
256         VERBOSE_PRINT (("Creating Directory \"%s\"\n", TargetPath));
257         if (mkdir (TargetPath))
258         {
259             if (errno != EEXIST)
260             {
261                 printf ("Could not create target directory\n");
262                 return (-1);
263             }
264         }
265     }
266
267     /* Do the C source files */
268
269     AsDoWildcard (ConversionTable, SourcePath, TargetPath, MaxPathLength,
270             FILE_TYPE_SOURCE, "*.c");
271
272     /* Do the C header files */
273
274     AsDoWildcard (ConversionTable, SourcePath, TargetPath, MaxPathLength,
275             FILE_TYPE_HEADER, "*.h");
276
277     /* Do the Lex file(s) */
278
279     AsDoWildcard (ConversionTable, SourcePath, TargetPath, MaxPathLength,
280             FILE_TYPE_SOURCE, "*.l");
281
282     /* Do the yacc file(s) */
283
284     AsDoWildcard (ConversionTable, SourcePath, TargetPath, MaxPathLength,
285             FILE_TYPE_SOURCE, "*.y");
286
287     /* Do any ASL files */
288
289     AsDoWildcard (ConversionTable, SourcePath, TargetPath, MaxPathLength,
290             FILE_TYPE_HEADER, "*.asl");
291
292     /* Do any subdirectories */
293
294     AsDoWildcard (ConversionTable, SourcePath, TargetPath, MaxPathLength,
295             FILE_TYPE_DIRECTORY, "*");
296
297     return (0);
298 }
299
300
301 /******************************************************************************
302  *
303  * FUNCTION:    AsDetectLoneLineFeeds
304  *
305  * DESCRIPTION: Find LF without CR.
306  *
307  ******************************************************************************/
308
309 BOOLEAN
310 AsDetectLoneLineFeeds (
311     char                    *Filename,
312     char                    *Buffer)
313 {
314     UINT32                  i = 1;
315     UINT32                  LfCount = 0;
316     UINT32                  LineCount = 0;
317
318
319     if (!Buffer[0])
320     {
321         return (FALSE);
322     }
323
324     while (Buffer[i])
325     {
326         if (Buffer[i] == 0x0A)
327         {
328             if (Buffer[i-1] != 0x0D)
329             {
330                 LfCount++;
331             }
332             LineCount++;
333         }
334         i++;
335     }
336
337     if (LfCount)
338     {
339         if (LineCount == LfCount)
340         {
341             if (!Gbl_IgnoreLoneLineFeeds)
342             {
343                 printf ("%s: ****File has UNIX format**** (LF only, not CR/LF) %u lines\n",
344                     Filename, LfCount);
345             }
346         }
347         else
348         {
349             printf ("%s: %u lone linefeeds in file\n", Filename, LfCount);
350         }
351         return (TRUE);
352     }
353
354     return (FALSE);
355 }
356
357
358 /******************************************************************************
359  *
360  * FUNCTION:    AsConvertFile
361  *
362  * DESCRIPTION: Perform the requested transforms on the file buffer (as
363  *              determined by the ConversionTable and the FileType).
364  *
365  ******************************************************************************/
366
367 void
368 AsConvertFile (
369     ACPI_CONVERSION_TABLE   *ConversionTable,
370     char                    *FileBuffer,
371     char                    *Filename,
372     ACPI_NATIVE_INT         FileType)
373 {
374     UINT32                  i;
375     UINT32                  Functions;
376     ACPI_STRING_TABLE       *StringTable;
377     ACPI_IDENTIFIER_TABLE   *ConditionalTable;
378     ACPI_IDENTIFIER_TABLE   *LineTable;
379     ACPI_IDENTIFIER_TABLE   *MacroTable;
380     ACPI_TYPED_IDENTIFIER_TABLE *StructTable;
381
382
383     switch (FileType)
384     {
385     case FILE_TYPE_SOURCE:
386         Functions           = ConversionTable->SourceFunctions;
387         StringTable         = ConversionTable->SourceStringTable;
388         LineTable           = ConversionTable->SourceLineTable;
389         ConditionalTable    = ConversionTable->SourceConditionalTable;
390         MacroTable          = ConversionTable->SourceMacroTable;
391         StructTable         = ConversionTable->SourceStructTable;
392        break;
393
394     case FILE_TYPE_HEADER:
395         Functions           = ConversionTable->HeaderFunctions;
396         StringTable         = ConversionTable->HeaderStringTable;
397         LineTable           = ConversionTable->HeaderLineTable;
398         ConditionalTable    = ConversionTable->HeaderConditionalTable;
399         MacroTable          = ConversionTable->HeaderMacroTable;
400         StructTable         = ConversionTable->HeaderStructTable;
401         break;
402
403     default:
404         printf ("Unknown file type, cannot process\n");
405         return;
406     }
407
408
409     Gbl_StructDefs = strstr (FileBuffer, "/* acpisrc:StructDefs");
410     Gbl_Files++;
411     VERBOSE_PRINT (("Processing %u bytes\n",
412         (unsigned int) strlen (FileBuffer)));
413
414     if (Gbl_Cleanup)
415     {
416         AsRemoveExtraLines (FileBuffer, Filename);
417         AsRemoveSpacesAfterPeriod (FileBuffer, Filename);
418     }
419
420     if (ConversionTable->LowerCaseTable)
421     {
422         for (i = 0; ConversionTable->LowerCaseTable[i].Identifier; i++)
423         {
424             AsLowerCaseString (ConversionTable->LowerCaseTable[i].Identifier,
425                                 FileBuffer);
426         }
427     }
428
429     /* Process all the string replacements */
430
431     if (StringTable)
432     {
433         for (i = 0; StringTable[i].Target; i++)
434         {
435             AsReplaceString (StringTable[i].Target, StringTable[i].Replacement,
436                     StringTable[i].Type, FileBuffer);
437         }
438     }
439
440     if (LineTable)
441     {
442         for (i = 0; LineTable[i].Identifier; i++)
443         {
444             AsRemoveLine (FileBuffer, LineTable[i].Identifier);
445         }
446     }
447
448     if (ConditionalTable)
449     {
450         for (i = 0; ConditionalTable[i].Identifier; i++)
451         {
452             AsRemoveConditionalCompile (FileBuffer, ConditionalTable[i].Identifier);
453         }
454     }
455
456     if (MacroTable)
457     {
458         for (i = 0; MacroTable[i].Identifier; i++)
459         {
460             AsRemoveMacro (FileBuffer, MacroTable[i].Identifier);
461         }
462     }
463
464     if (StructTable)
465     {
466         for (i = 0; StructTable[i].Identifier; i++)
467         {
468             AsInsertPrefix (FileBuffer, StructTable[i].Identifier, StructTable[i].Type);
469         }
470     }
471
472     /* Process the function table */
473
474     for (i = 0; i < 32; i++)
475     {
476         /* Decode the function bitmap */
477
478         switch ((1 << i) & Functions)
479         {
480         case 0:
481             /* This function not configured */
482             break;
483
484
485         case CVT_COUNT_TABS:
486
487             AsCountTabs (FileBuffer, Filename);
488             break;
489
490
491         case CVT_COUNT_NON_ANSI_COMMENTS:
492
493             AsCountNonAnsiComments (FileBuffer, Filename);
494             break;
495
496
497         case CVT_CHECK_BRACES:
498
499             AsCheckForBraces (FileBuffer, Filename);
500             break;
501
502
503         case CVT_TRIM_LINES:
504
505             AsTrimLines (FileBuffer, Filename);
506             break;
507
508
509         case CVT_COUNT_LINES:
510
511             AsCountSourceLines (FileBuffer, Filename);
512             break;
513
514
515         case CVT_BRACES_ON_SAME_LINE:
516
517             AsBracesOnSameLine (FileBuffer);
518             break;
519
520
521         case CVT_MIXED_CASE_TO_UNDERSCORES:
522
523             AsMixedCaseToUnderscores (FileBuffer, Filename);
524             break;
525
526
527         case CVT_LOWER_CASE_IDENTIFIERS:
528
529             AsLowerCaseIdentifiers (FileBuffer);
530             break;
531
532
533         case CVT_REMOVE_DEBUG_MACROS:
534
535             AsRemoveDebugMacros (FileBuffer);
536             break;
537
538
539         case CVT_TRIM_WHITESPACE:
540
541             AsTrimWhitespace (FileBuffer);
542             break;
543
544
545         case CVT_REMOVE_EMPTY_BLOCKS:
546
547             AsRemoveEmptyBlocks (FileBuffer, Filename);
548             break;
549
550
551         case CVT_REDUCE_TYPEDEFS:
552
553             AsReduceTypedefs (FileBuffer, "typedef union");
554             AsReduceTypedefs (FileBuffer, "typedef struct");
555             break;
556
557
558         case CVT_SPACES_TO_TABS4:
559
560             AsTabify4 (FileBuffer);
561             break;
562
563
564         case CVT_SPACES_TO_TABS8:
565
566             AsTabify8 (FileBuffer);
567             break;
568
569         case CVT_COUNT_SHORTMULTILINE_COMMENTS:
570
571 #ifdef ACPI_FUTURE_IMPLEMENTATION
572             AsTrimComments (FileBuffer, Filename);
573 #endif
574             break;
575
576         default:
577
578             printf ("Unknown conversion subfunction opcode\n");
579             break;
580         }
581     }
582
583     if (ConversionTable->NewHeader)
584     {
585         AsReplaceHeader (FileBuffer, ConversionTable->NewHeader);
586     }
587 }
588
589
590 /******************************************************************************
591  *
592  * FUNCTION:    AsProcessOneFile
593  *
594  * DESCRIPTION: Process one source file. The file is opened, read entirely
595  *              into a buffer, converted, then written to a new file.
596  *
597  ******************************************************************************/
598
599 ACPI_NATIVE_INT
600 AsProcessOneFile (
601     ACPI_CONVERSION_TABLE   *ConversionTable,
602     char                    *SourcePath,
603     char                    *TargetPath,
604     int                     MaxPathLength,
605     char                    *Filename,
606     ACPI_NATIVE_INT         FileType)
607 {
608     char                    *Pathname;
609     char                    *OutPathname = NULL;
610
611
612     /* Allocate a file pathname buffer for both source and target */
613
614     Pathname = calloc (MaxPathLength + strlen (Filename) + 2, 1);
615     if (!Pathname)
616     {
617         printf ("Could not allocate buffer for file pathnames\n");
618         return (-1);
619     }
620
621     Gbl_FileType = FileType;
622
623     /* Generate the source pathname and read the file */
624
625     if (SourcePath)
626     {
627         strcpy (Pathname, SourcePath);
628         strcat (Pathname, "/");
629     }
630
631     strcat (Pathname, Filename);
632
633     if (AsGetFile (Pathname, &Gbl_FileBuffer, &Gbl_FileSize))
634     {
635         return (-1);
636     }
637
638     Gbl_HeaderSize = 0;
639     if (strstr (Filename, ".asl"))
640     {
641         Gbl_HeaderSize = LINES_IN_ASL_HEADER; /* Lines in default ASL header */
642     }
643     else if (strstr (Gbl_FileBuffer, LEGAL_HEADER_SIGNATURE))
644     {
645         Gbl_HeaderSize = LINES_IN_LEGAL_HEADER; /* Normal C file and H header */
646     }
647     else if (strstr (Gbl_FileBuffer, LINUX_HEADER_SIGNATURE))
648     {
649         Gbl_HeaderSize = LINES_IN_LINUX_HEADER; /* Linuxized C file and H header */
650     }
651
652     /* Process the file in the buffer */
653
654     Gbl_MadeChanges = FALSE;
655     if (!Gbl_IgnoreLoneLineFeeds && Gbl_HasLoneLineFeeds)
656     {
657         /*
658          * All lone LFs will be converted to CR/LF
659          * (when file is written, Windows version only)
660          */
661         printf ("Converting lone linefeeds\n");
662         Gbl_MadeChanges = TRUE;
663     }
664
665     AsConvertFile (ConversionTable, Gbl_FileBuffer, Pathname, FileType);
666
667     if (!(ConversionTable->Flags & FLG_NO_FILE_OUTPUT))
668     {
669         if (!(Gbl_Overwrite && !Gbl_MadeChanges))
670         {
671             /* Generate the target pathname and write the file */
672
673             OutPathname = calloc (MaxPathLength + strlen (Filename) + 2 + strlen (TargetPath), 1);
674             if (!OutPathname)
675             {
676                 printf ("Could not allocate buffer for file pathnames\n");
677                 return (-1);
678             }
679
680             strcpy (OutPathname, TargetPath);
681             if (SourcePath)
682             {
683                 strcat (OutPathname, "/");
684                 strcat (OutPathname, Filename);
685             }
686
687             AsPutFile (OutPathname, Gbl_FileBuffer, ConversionTable->Flags);
688         }
689     }
690
691     free (Gbl_FileBuffer);
692     free (Pathname);
693     if (OutPathname)
694     {
695         free (OutPathname);
696     }
697
698     return (0);
699 }
700
701
702 /******************************************************************************
703  *
704  * FUNCTION:    AsCheckForDirectory
705  *
706  * DESCRIPTION: Check if the current file is a valid directory. If not,
707  *              construct the full pathname for the source and target paths.
708  *              Checks for the dot and dot-dot files (they are ignored)
709  *
710  ******************************************************************************/
711
712 ACPI_NATIVE_INT
713 AsCheckForDirectory (
714     char                    *SourceDirPath,
715     char                    *TargetDirPath,
716     char                    *Filename,
717     char                    **SourcePath,
718     char                    **TargetPath)
719 {
720     char                    *SrcPath;
721     char                    *TgtPath;
722
723
724     if (!(strcmp (Filename, ".")) ||
725         !(strcmp (Filename, "..")))
726     {
727         return (-1);
728     }
729
730     SrcPath = calloc (strlen (SourceDirPath) + strlen (Filename) + 2, 1);
731     if (!SrcPath)
732     {
733         printf ("Could not allocate buffer for directory source pathname\n");
734         return (-1);
735     }
736
737     TgtPath = calloc (strlen (TargetDirPath) + strlen (Filename) + 2, 1);
738     if (!TgtPath)
739     {
740         printf ("Could not allocate buffer for directory target pathname\n");
741         free (SrcPath);
742         return (-1);
743     }
744
745     strcpy (SrcPath, SourceDirPath);
746     strcat (SrcPath, "/");
747     strcat (SrcPath, Filename);
748
749     strcpy (TgtPath, TargetDirPath);
750     strcat (TgtPath, "/");
751     strcat (TgtPath, Filename);
752
753     *SourcePath = SrcPath;
754     *TargetPath = TgtPath;
755     return (0);
756 }
757
758
759 /******************************************************************************
760  *
761  * FUNCTION:    AsGetFile
762  *
763  * DESCRIPTION: Open a file and read it entirely into a an allocated buffer
764  *
765  ******************************************************************************/
766
767 int
768 AsGetFile (
769     char                    *Filename,
770     char                    **FileBuffer,
771     UINT32                  *FileSize)
772 {
773
774     int                     FileHandle;
775     UINT32                  Size;
776     char                    *Buffer;
777
778
779     /* Binary mode leaves CR/LF pairs */
780
781     FileHandle = open (Filename, O_BINARY | O_RDONLY);
782     if (!FileHandle)
783     {
784         printf ("Could not open %s\n", Filename);
785         return (-1);
786     }
787
788     if (fstat (FileHandle, &Gbl_StatBuf))
789     {
790         printf ("Could not get file status for %s\n", Filename);
791         goto ErrorExit;
792     }
793
794     /*
795      * Create a buffer for the entire file
796      * Add plenty extra buffer to accommodate string replacements
797      */
798     Size = Gbl_StatBuf.st_size;
799     Gbl_TotalSize += Size;
800
801     Buffer = calloc (Size * 2, 1);
802     if (!Buffer)
803     {
804         printf ("Could not allocate buffer of size %u\n", Size * 2);
805         goto ErrorExit;
806     }
807
808     /* Read the entire file */
809
810     Size = read (FileHandle, Buffer, Size);
811     if (Size == -1)
812     {
813         printf ("Could not read the input file %s\n", Filename);
814         goto ErrorExit;
815     }
816
817     Buffer [Size] = 0;         /* Null terminate the buffer */
818     close (FileHandle);
819
820     /* Check for unix contamination */
821
822     Gbl_HasLoneLineFeeds = AsDetectLoneLineFeeds (Filename, Buffer);
823
824     /*
825      * Convert all CR/LF pairs to LF only. We do this locally so that
826      * this code is portable across operating systems.
827      */
828     AsConvertToLineFeeds (Buffer);
829
830     *FileBuffer = Buffer;
831     *FileSize = Size;
832
833     return (0);
834
835
836 ErrorExit:
837
838     close (FileHandle);
839     return (-1);
840 }
841
842
843 /******************************************************************************
844  *
845  * FUNCTION:    AsPutFile
846  *
847  * DESCRIPTION: Create a new output file and write the entire contents of the
848  *              buffer to the new file. Buffer must be a zero terminated string
849  *
850  ******************************************************************************/
851
852 int
853 AsPutFile (
854     char                    *Pathname,
855     char                    *FileBuffer,
856     UINT32                  SystemFlags)
857 {
858     UINT32                  FileSize;
859     int                     DestHandle;
860     int                     OpenFlags;
861
862
863     /* Create the target file */
864
865     OpenFlags = O_TRUNC | O_CREAT | O_WRONLY | O_BINARY;
866
867     if (!(SystemFlags & FLG_NO_CARRIAGE_RETURNS))
868     {
869         /* Put back the CR before each LF */
870
871         AsInsertCarriageReturns (FileBuffer);
872     }
873
874     DestHandle = open (Pathname, OpenFlags, S_IREAD | S_IWRITE);
875     if (DestHandle == -1)
876     {
877         perror ("Could not create destination file");
878         printf ("Could not create destination file \"%s\"\n", Pathname);
879         return (-1);
880     }
881
882     /* Write the buffer to the file */
883
884     FileSize = strlen (FileBuffer);
885     if (write (DestHandle, FileBuffer, FileSize) == -1)
886     {
887         printf ("Error writing output file \"%s\"\n", Pathname);
888     }
889
890     close (DestHandle);
891     return (0);
892 }