📄 gcc.texi
字号:
does mean that there's nothing for us to do about them.
@end itemize
@node Standard Libraries
@section Standard Libraries
@opindex Wall
GCC by itself attempts to be a conforming freestanding implementation.
@xref{Standards,,Language Standards Supported by GCC}, for details of
what this means. Beyond the library facilities required of such an
implementation, the rest of the C library is supplied by the vendor of
the operating system. If that C library doesn't conform to the C
standards, then your programs might get warnings (especially when using
@option{-Wall}) that you don't expect.
For example, the @code{sprintf} function on SunOS 4.1.3 returns
@code{char *} while the C standard says that @code{sprintf} returns an
@code{int}. The @code{fixincludes} program could make the prototype for
this function match the Standard, but that would be wrong, since the
function will still return @code{char *}.
If you need a Standard compliant library, then you need to find one, as
GCC does not provide one. The GNU C library (called @code{glibc})
provides ISO C, POSIX, BSD, SystemV and X/Open compatibility for
GNU/Linux and HURD-based GNU systems; no recent version of it supports
other systems, though some very old versions did. Version 2.2 of the
GNU C library includes nearly complete C99 support. You could also ask
your operating system vendor if newer libraries are available.
@node Disappointments
@section Disappointments and Misunderstandings
These problems are perhaps regrettable, but we don't know any practical
way around them.
@itemize @bullet
@item
Certain local variables aren't recognized by debuggers when you compile
with optimization.
This occurs because sometimes GCC optimizes the variable out of
existence. There is no way to tell the debugger how to compute the
value such a variable ``would have had'', and it is not clear that would
be desirable anyway. So GCC simply does not mention the eliminated
variable when it writes debugging information.
You have to expect a certain amount of disagreement between the
executable and your source code, when you use optimization.
@cindex conflicting types
@cindex scope of declaration
@item
Users often think it is a bug when GCC reports an error for code
like this:
@example
int foo (struct mumble *);
struct mumble @{ @dots{} @};
int foo (struct mumble *x)
@{ @dots{} @}
@end example
This code really is erroneous, because the scope of @code{struct
mumble} in the prototype is limited to the argument list containing it.
It does not refer to the @code{struct mumble} defined with file scope
immediately below---they are two unrelated types with similar names in
different scopes.
But in the definition of @code{foo}, the file-scope type is used
because that is available to be inherited. Thus, the definition and
the prototype do not match, and you get an error.
This behavior may seem silly, but it's what the ISO standard specifies.
It is easy enough for you to make your code work by moving the
definition of @code{struct mumble} above the prototype. It's not worth
being incompatible with ISO C just to avoid an error for the example
shown above.
@item
Accesses to bit-fields even in volatile objects works by accessing larger
objects, such as a byte or a word. You cannot rely on what size of
object is accessed in order to read or write the bit-field; it may even
vary for a given bit-field according to the precise usage.
If you care about controlling the amount of memory that is accessed, use
volatile but do not use bit-fields.
@item
GCC comes with shell scripts to fix certain known problems in system
header files. They install corrected copies of various header files in
a special directory where only GCC will normally look for them. The
scripts adapt to various systems by searching all the system header
files for the problem cases that we know about.
If new system header files are installed, nothing automatically arranges
to update the corrected header files. You will have to reinstall GCC
to fix the new header files. More specifically, go to the build
directory and delete the files @file{stmp-fixinc} and
@file{stmp-headers}, and the subdirectory @code{include}; then do
@samp{make install} again.
@item
@cindex floating point precision
On 68000 and x86 systems, for instance, you can get paradoxical results
if you test the precise values of floating point numbers. For example,
you can find that a floating point value which is not a NaN is not equal
to itself. This results from the fact that the floating point registers
hold a few more bits of precision than fit in a @code{double} in memory.
Compiled code moves values between memory and floating point registers
at its convenience, and moving them into memory truncates them.
@opindex ffloat-store
You can partially avoid this problem by using the @option{-ffloat-store}
option (@pxref{Optimize Options}).
@item
On the MIPS, variable argument functions using @file{varargs.h}
cannot have a floating point value for the first argument. The
reason for this is that in the absence of a prototype in scope,
if the first argument is a floating point, it is passed in a
floating point register, rather than an integer register.
If the code is rewritten to use the ISO standard @file{stdarg.h}
method of variable arguments, and the prototype is in scope at
the time of the call, everything will work fine.
@item
On the H8/300 and H8/300H, variable argument functions must be
implemented using the ISO standard @file{stdarg.h} method of
variable arguments. Furthermore, calls to functions using @file{stdarg.h}
variable arguments must have a prototype for the called function
in scope at the time of the call.
@end itemize
@node C++ Misunderstandings
@section Common Misunderstandings with GNU C++
@cindex misunderstandings in C++
@cindex surprises in C++
@cindex C++ misunderstandings
C++ is a complex language and an evolving one, and its standard
definition (the ISO C++ standard) was only recently completed. As a
result, your C++ compiler may occasionally surprise you, even when its
behavior is correct. This section discusses some areas that frequently
give rise to questions of this sort.
@menu
* Static Definitions:: Static member declarations are not definitions
* Temporaries:: Temporaries may vanish before you expect
* Copy Assignment:: Copy Assignment operators copy virtual bases twice
@end menu
@node Static Definitions
@subsection Declare @emph{and} Define Static Members
@cindex C++ static data, declaring and defining
@cindex static data in C++, declaring and defining
@cindex declaring static data in C++
@cindex defining static data in C++
When a class has static data members, it is not enough to @emph{declare}
the static member; you must also @emph{define} it. For example:
@example
class Foo
@{
@dots{}
void method();
static int bar;
@};
@end example
This declaration only establishes that the class @code{Foo} has an
@code{int} named @code{Foo::bar}, and a member function named
@code{Foo::method}. But you still need to define @emph{both}
@code{method} and @code{bar} elsewhere. According to the ISO
standard, you must supply an initializer in one (and only one) source
file, such as:
@example
int Foo::bar = 0;
@end example
Other C++ compilers may not correctly implement the standard behavior.
As a result, when you switch to @code{g++} from one of these compilers,
you may discover that a program that appeared to work correctly in fact
does not conform to the standard: @code{g++} reports as undefined
symbols any static data members that lack definitions.
@node Temporaries
@subsection Temporaries May Vanish Before You Expect
@cindex temporaries, lifetime of
@cindex portions of temporary objects, pointers to
It is dangerous to use pointers or references to @emph{portions} of a
temporary object. The compiler may very well delete the object before
you expect it to, leaving a pointer to garbage. The most common place
where this problem crops up is in classes like string classes,
especially ones that define a conversion function to type @code{char *}
or @code{const char *}---which is one reason why the standard
@code{string} class requires you to call the @code{c_str} member
function. However, any class that returns a pointer to some internal
structure is potentially subject to this problem.
For example, a program may use a function @code{strfunc} that returns
@code{string} objects, and another function @code{charfunc} that
operates on pointers to @code{char}:
@example
string strfunc ();
void charfunc (const char *);
void
f ()
@{
const char *p = strfunc().c_str();
@dots{}
charfunc (p);
@dots{}
charfunc (p);
@}
@end example
@noindent
In this situation, it may seem reasonable to save a pointer to the C
string returned by the @code{c_str} member function and use that rather
than call @code{c_str} repeatedly. However, the temporary string
created by the call to @code{strfunc} is destroyed after @code{p} is
initialized, at which point @code{p} is left pointing to freed memory.
Code like this may run successfully under some other compilers,
particularly obsolete cfront-based compilers that delete temporaries
along with normal local variables. However, the GNU C++ behavior is
standard-conforming, so if your program depends on late destruction of
temporaries it is not portable.
The safe way to write such code is to give the temporary a name, which
forces it to remain until the end of the scope of the name. For
example:
@example
string& tmp = strfunc ();
charfunc (tmp.c_str ());
@end example
@node Copy Assignment
@subsection Implicit Copy-Assignment for Virtual Bases
When a base class is virtual, only one subobject of the base class
belongs to each full object. Also, the constructors and destructors are
invoked only once, and called from the most-derived class. However, such
objects behave unspecified when being assigned. For example:
@example
struct Base@{
char *name;
Base(char *n) : name(strdup(n))@{@}
Base& operator= (const Base& other)@{
free (name);
name = strdup (other.name);
@}
@};
struct A:virtual Base@{
int val;
A():Base("A")@{@}
@};
struct B:virtual Base@{
int bval;
B():Base("B")@{@}
@};
struct Derived:public A, public B@{
Derived():Base("Derived")@{@}
@};
void func(Derived &d1, Derived &d2)
@{
d1 = d2;
@}
@end example
The C++ standard specifies that @samp{Base::Base} is only called once
when constructing or copy-constructing a Derived object. It is
unspecified whether @samp{Base::operator=} is called more than once when
the implicit copy-assignment for Derived objects is invoked (as it is
inside @samp{func} in the example).
g++ implements the ``intuitive'' algorithm for copy-assignment: assign all
direct bases, then assign all members. In that algorithm, the virtual
base subobject can be encountered many times. In the example, copying
proceeds in the following order: @samp{val}, @samp{name} (via
@code{strdup}), @samp{bval}, and @samp{name} again.
If application code relies on copy-assignment, a user-defined
copy-assignment operator removes any uncertainties. With such an
operator, the application can define whether and how the virtual base
subobject is assigned.
@node Protoize Caveats
@section Caveats of using @command{protoize}
The conversion programs @command{protoize} and @command{unprotoize} can
sometimes change a source file in a way that won't work unless you
rearrange it.
@itemize @bullet
@item
@command{protoize} can insert references to a type name or type tag before
the definition, or in a file where they are not defined.
If this happens, compiler error messages should show you where the new
references are, so fixing the file by hand is straightforward.
@item
There are some C constructs which @command{protoize} cannot figure out.
For example, it can't determine argument types for declaring a
pointer-to-function variable; this you must do by hand. @command{protoize}
inserts a comment containing @samp{???} each time it finds such a
variable; so you can find all such variables by searching for this
string. ISO C does not require declaring the argument types of
pointer-to-function types.
@item
Using @command{unprotoize} can easily introduce bugs. If the program
relied on prototypes to bring about conversion of arguments, these
conversions will not take place in the program without prototypes.
One case in which you can be sure @command{unprotoize} is safe is when
you are removing prototypes that were made with @command{protoize}; if
the program worked before without any prototypes, it will work again
without them.
@opindex Wconversion
You can find all the places where th
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -