g++ -E option output - c++

Using this option I receive files after preprocessing. There are many lines like:
# 91 "/usr/include/stdint.h" 3 4
What do the numbers mean? First I thought that #91 is the number of line where file is included, but that is not it. And about 3 4 I have no idea at all.

According to the official documentation, the line is of the format:
# linenum filename flags
The linenum specifies that the following line originated in filename at that line number. Then there are four flags:
1 - Start of a new file
2 - Returning to a file
3 - System header file
4 - Treat as being wrapped in extern "C"
So let's interpret your linemarker:
# 91 "/usr/include/stdint.h" 3 4
The following line originated from line 91 of /usr/include/stdint.h. It is a system header file and should be treated as wrapped in extern "C".

These are called "line markers". From the documentation:
Source file name and line number information is conveyed by lines of the form
# linenum filename flags
These are called linemarkers. They are inserted as needed into the output (but never within a string or character constant). They mean that the following line originated in file filename at line linenum. filename will never contain any non-printing characters; they are replaced with octal escape sequences.
After the file name comes zero or more flags, which are ‘1’, ‘2’, ‘3’, or ‘4’. If there are multiple flags, spaces separate them. Here is what the flags mean:
‘1’ -
This indicates the start of a new file.
‘2’ -
This indicates returning to a file (after having included another file).
‘3’ -
This indicates that the following text comes from a system header file, so certain warnings should be suppressed.
‘4’ -
This indicates that the following text should be treated as being wrapped in an implicit extern "C" block.

There are flags (space separated) and the meaning is:
1 - Start of a new file
2 - Returning to previous file
3 - Following text comes from a system header file (#include <> vs #include "")
4 - Following text should be treated as being wrapped in an implicit extern "C" block.

Related

What do the lines starting with # symbol in g++ -E generated translation unit [duplicate]

This question already has an answer here:
How to interpret #-prefixed lines in C preprocessor output?
(1 answer)
Closed 4 years ago.
I tried to check the translation unit generated for a simple hello world program looks like.
So, I wrote below code in test.cpp.
#include <iostream>
using namespace std;
int main()
{
cout<<"Hello World"<<endl;
}
I then compiled the above file with g++ with -E option and output the data to a temp file.
The file has c++ code with lines in between starting with # symbols.
Something like below,
# 1 "test.cpp"
# 1 "<built-in>"
# 1 "<command-line>"
# 1 "/usr/include/stdc-predef.h" 1 3 4
# 1 "<command-line>" 2
# 1 "test.cpp"
# 1 "/usr/include/c++/8/iostream" 1 3
# 36 "/usr/include/c++/8/iostream" 3
What do these lines mean ?
Is there any document that I should read or do I have to get knowledge in any specific subject to understand this file?
http://tigcc.ticalc.org/doc/comopts.html
-E
Stop after the preprocessing stage; do not run the compiler proper. The output is in the form of preprocessed source code, which
is sent to the standard output.
Input files which don't require preprocessing are ignored.
Then you can find "Preprocessor Output" in gcc documentation:
# linenum filename flags
These are called linemarkers. They are inserted as needed into the
output (but never within a string or character constant). They mean
that the following line originated in file filename at line linenum.
filename will never contain any non-printing characters; they are
replaced with octal escape sequences.
After the file name comes zero or more flags, which are ‘1’, ‘2’, ‘3’,
or ‘4’. If there are multiple flags, spaces separate them. Here is
what the flags mean:
‘1’ This indicates the start of a new file.
‘2’ This indicates returning to a file (after having included another file).
‘3’ This indicates that the following text comes from a system header file, so certain warnings should be suppressed.
‘4’ This indicates that the following text should be treated as being wrapped in an implicit extern "C" block.
Line number information.
If you compile the preprocessed output, those can.be used to find the line numbers and files of the original source.

Checking an external file against set of functions and printing error alongwith line number using c++

I have a GEDCOM file, which I am supplying to my program, my program checks the content of GEDCOM file against a set of functions.
If the contents of file, fail to match the requirements of function, it should throw an error along with the line number on the GEDCOM file where error exists.
I would also like to mention that I have tried using macros like LINE, FILE but they are printing the contents of source code like line of source code and file name of source code.
Thanks in advance
If you are reading the file one line at a time you can keep a counter of the number of lines you have read from the file.
If you already have the whole file in one big buffer you can scan the number of newline or return characters.
If you provide a MCV example demonstrating your code reading in the file I can maybe help more.

Insert in a file without overwriting without using a 2nd file using C/C++

The below are the contents in a text file.
name1: 1234
name2: 2000
name3: 3000
This is an existing text file and I want to replace one value(say 1234) with another value (say 12345) in the text file. so I placed the cursor at start of the value (here its the 7th position) . Then i used the following statement:
fprintf(filepointer,"12345\n");
The resultant file is like
name1: 12345
ame2 : 2000
name3 : 3000
Its overwriting the 4 characters("1000") and a newline('\n') and 'n' with 5 characters("12345") and a newline('\n').
The solutions I know are:
1. Overwriting the entire file to add one extra character.
2. Copying each line in a linked list node and change the characters in the memory and write in the same file.
3. Create a temp file and copy the new characters to the desired place in the temp file and change the name of the temp file to source file name and delete the source file.
Also I tried adding carriage return '\r' and windows format of EOF ('\r\n') , still the next line characters are overwritten. Also I expanded the file size using [SetEndOfFile][1] API and still I face the same problem. I searched many forums and found answers like "It is not possible to insert characters without overwriting".
Is there any solution just to insert characters without overwriting the characters in the middle of the file. or any logic to insert characters in a line and not affect the next line.
Thanks in advance.
Is it possible Using visual studio VC++ ??
Thanks:)
A sequential file is ehh... just sequential. All the bytes follow each other with no notion of line or any other structure.
The only operations allowed by the underlying file system are (only speaking of writing):
replace bytes anywhere in the file
add bytes at the end of the file
truncate the file (or add random(*) bytes at the end by moving the end of file
There is no provision for insertion in the middle so no language will be able to do that (except by doing overwriting under the hood)
(*) if you move the end of file forward more than one logical block (file system sense) many file systems will create a hole that is a phantom block that does not use any space on disk and is read as null bytes
Is there any solution just to insert characters without overwriting
the characters in the middle of the file. or any logic to insert
characters in a line and not affect the next line.
No, what you ask for is not possible with any file system I've ever used.
Use method (3), a temp file. Use a temp file with a different, unique extension added/replaced, eg '.tmp', so that the temp files can be recognised on startup, then:
1) Get source file name, eg. 'source.txt'
2) Append, or replace a '.tmp' extension: 'source.txt.tmp'
3) Open the two files
4) Read the source, modify, write the temp
5) Close both
6) Delete source file
7) rename temp file
When you program starts:
1) search for files with '.tmp' extension.
2) if found, eg. 'source.txt.tmp', take the file name and remove the extension, eg 'source.txt'
3) Test if a file with that name exists
4) If so, delete the temp file
5) If not, rename the temp file
Result: if the process crashes, you end up with either an intact, unmodified source file, or an intact, modified source file.

Understanding and parsing warnings from gcc

When compiling a .cpp file from Emacs through M-x compile (which runs the folder's Makefile), I see the following on the compilation buffer (displayed in compilation mode):
In file included from: /path/to/file1:60,
from /path/to/file2.h:15,
from /path/to/file3.cpp:16:
/path/to/file4.h:28:2: #warning This file includes at least one deprecated or antiquated header which may be removed without
further notice at a future date. Please use a non-deprecated interface
with equivalent functionality instead. For a listing of replacement
headers and interfaces, consult the file backward_warning.h. To
disable this warning use -Wno-deprecated.
Aside from the actual warning message, how should I understand this trace? i.e. which file generated the warning? (file1,file2, file3 or file4)?
Also, why is there a comma after the file2 line, a colon after the file3 line, the line with file4 includes two numbers separated with two colons?
I am using Emacs 24.2.1, with gcc-4.4.5-x86_64.
The construct that actually triggered the warning (a #warning preprocessor directive, in this case) is in file4. The stuff above that is a trace of the #include stack, innermost-but-one first: in this case, file3 included file2, which included file1, which included file4.
When gcc knows the column number of the construct that triggered a diagnostic, it prints the file name, a colon, the line number, another colon, and the column number, as you see on the file4 line. The first number is the line number (28) and the second number is the column number (in this case, you will find that the # of #warning is in column 2). When gcc doesn't know the column number, it just prints the file name, a colon, and the line number. This is the case for the #include stack, as it does not bother recording the exact column of #include directives. Emacs' compilation-mode understands how to parse both these syntaxes: you will find that if you use C-x ` to page through the diagnostics, when there is a column number available, Emacs will place the cursor at the appropriate column.
The colons and commas at the ends of these reports are just to conform to English punctuation convention; they don't mean anything.
The warning was generated in file4.h, on line 28.
The comma is because you're in the middle of a list, the colon designates the end of the list. The two numbers are line number and column number.
Actually show its compilation path saying that:
in column 2 of line 28 of file4.h
that included from file1.h(line 60)
that included from file2.h(line 15)
that included from file3.cpp(line 16)
there was a warning ...
Every compiler should keep this track and it has nothing to do with GCC is smart or something!!
Since your compiler only compile file3.cpp and every other file will only parsed as a result of inclusion from this file.

What does #line mean?

What does the following line do?
#line 25 "CSSGrammar.y"
And what's with the extension?
According to the Standard:
§16.4.3:
A preprocessing directive of the form
# line digit-sequence new-line
causes the implementation to behave as if the following sequence of source lines begins with a source line
that has a line number as specified by the digit sequence (interpreted as a decimal integer). If the digit
sequence specifies zero or a number greater than 2147483647, the behavior is undefined.
§16.4.4:
A preprocessing directive of the form
# line digit-sequence " s-char-sequenceopt" new-line
sets the presumed line number similarly and changes the presumed name of the source file to be the contents
of the character string literal.
§16.4.5:
A preprocessing directive of the form
# line pp-tokens new-line
(that does not match one of the two previous forms) is permitted. The preprocessing tokens after line
on the directive are processed just as in normal text (each identifier currently defined as a macro name is
replaced by its replacement list of preprocessing tokens). If the directive resulting after all replacements
does not match one of the two previous forms, the behavior is undefined; otherwise, the result is processed
as appropriate.
The .y extension is just what the author chose to use, perhaps to make it apparent that it was a YACC file (the word "grammar" also points to that though it's just a guess).
It simply states that the current line of code is sourced from line 25 of CSSGrammar.y, a YACC-style grammar file which is where this code was generated.
This can be used by debuggers to step into the grammar itself as opposed to the generated code.
#line directive modifies the reporting position for the compiler, and is used by code generating software to help the programmer identify the issue in the original source. It can be used by anyone to help redirect error reporting to be more informative.
So for instance your parser generates a CSSGrammar.cpp file say, which is compiled by the c++ compiler, and has c++ snippets in it, a #line 25 "CSSGrammar.y" directive tells the c++ compiler to treat that particular point in the file as if it is line number 25 from CSSGrammar.y
The compiler will continue to parse subsequent lines and report errors under the initial conditions of that directive.
So if an error occurs 3 lines later it would report that an error occurred on line 28 in CSSGrammar.y
Note that a single source file can have sources coming in from multiple parts; and that this directive can be used quite effectively to indicate error conditions.
Typically you'll see that there are multiple #line directives along the way; they are just there to account for various injections along the way (to reset the reporting caret if you will).
Note that #line directive can be used by ANY generator including your own, and is not limited to in anyway parser generators.
It a directive for the compiler to believe that the following line is the line number 25 in file CSSGrammar.y. Then, if an error is detected by the compiler on the 2nd next line, it would be reported as coming from line 26 of CSSGrammar.y
Programs generating C files, like bison, or yacc, or flex, or ANTLR, or even the (obsolete) MELT use that possibility a lot.
If debugging information is generated (e.g. with gcc -g), it will point to the CSSGrammar.y file in your example.
The 'yacc' parser generator consumes files that end in .y, and emits files that contain c or c++. It adds these #line lines to allow a debugger to get back to ye olde original source, accept no substitutes.
it's a c preprocessor option. It tells the c-parser to drop it's line count of the source file an pretend, that this is line #25.
With this information it's easier for you to debug the the source file. The yacc file will be translated into a c-source, where this is the pretended source line.
Using #line forces the compiler to experience amnesia about what file it's compiling and what line it's on, and loads in the new data.
Note: The compiler still compiles from the line it was on.