X-Git-Url: http://demsky.eecs.uci.edu/git/?a=blobdiff_plain;f=docs%2FCodingStandards.html;h=a99e46e5b5801c5dc8acfb113542533125e26cd5;hb=8cb8245cf117fc4a4f0a6549d9a773a12895550c;hp=cec26fa67c6867dc30f2339e2d55ff7c8745dbb8;hpb=f55914a5292a0b163d4b05069b983da08c1e3f16;p=oota-llvm.git diff --git a/docs/CodingStandards.html b/docs/CodingStandards.html index cec26fa67c6..a99e46e5b58 100644 --- a/docs/CodingStandards.html +++ b/docs/CodingStandards.html @@ -41,12 +41,15 @@
  • #include as Little as Possible
  • Keep "internal" Headers Private
  • +
  • #include <iostream> is + forbidden
  • The Low Level Issues
    1. Assert Liberally
    2. Do not use 'using namespace std'
    3. -
    4. Provide a virtual method anchor for clases in headers
    5. +
    6. Provide a virtual method anchor for + classes in headers
    7. Prefer Preincrement
    8. Avoid std::endl
  • @@ -55,7 +58,8 @@
    -

    Written by Chris Lattner

    +

    Written by Chris Lattner and + Bill Wendling

    @@ -118,9 +122,9 @@ documentation is very useful:

    File Headers -

    Every source file should have a header on it that -describes the basic purpose of the file. If a file does not have a header, it -should not be checked into CVS. Most source trees will probably have a standard +

    Every source file should have a header on it that describes the basic +purpose of the file. If a file does not have a header, it should not be +checked into Subversion. Most source trees will probably have a standard file header format. The standard format for the LLVM source tree looks like this:

    @@ -130,8 +134,8 @@ this:

    // // The LLVM Compiler Infrastructure // -// This file was developed by the LLVM research group and is distributed under -// the University of Illinois Open Source License. See LICENSE.TXT for details. +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. // //===----------------------------------------------------------------------===// // @@ -150,9 +154,9 @@ on the first line, along with a very short description of the purpose of the file. This is important when printing out code and flipping though lots of pages.

    -

    The next section in the file is a concise note that defines the license that -the file is released under. This makes it perfectly clear what terms the source -code can be distributed under.

    +

    The next section in the file is a concise note that defines the license +that the file is released under. This makes it perfectly clear what terms the +source code can be distributed under and should not be modified in any way.

    The main body of the description does not have to be very long in most cases. Here it's only two lines. If an algorithm is being implemented or something @@ -452,7 +456,8 @@ most cases, you simply don't need the definition of a class... and not #include'ing speeds up compilation.

    It is easy to try to go too overboard on this recommendation, however. You -must include all of the header files that you are using, either directly +must include all of the header files that you are using -- you can +include them either directly or indirectly (through another header file). To make sure that you don't accidently forget to include a header file in your module header, make sure to include your module header first in the implementation file (as mentioned @@ -482,6 +487,90 @@ class itself... just make them private (or protected), and all is well.

    + +
    + #include <iostream> is forbidden +
    + +
    + +

    The use of #include <iostream> in library files is +hereby forbidden. The primary reason for doing this is to +support clients using LLVM libraries as part of larger systems. In particular, +we statically link LLVM into some dynamic libraries. Even if LLVM isn't used, +the static c'tors are run whenever an application start up that uses the dynamic +library. There are two problems with this:

    + +
      +
    1. The time to run the static c'tors impacts startup time of + applications—a critical time for GUI apps.
    2. +
    3. The static c'tors cause the app to pull many extra pages of memory off the + disk: both the code for the static c'tors in each .o file and the + small amount of data that gets touched. In addition, touched/dirty pages + put more pressure on the VM system on low-memory machines.
    4. +
    + +
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    Old WayNew Way
    #include <iostream>
    #include "llvm/Support/Streams.h"
    DEBUG(std::cerr << ...);
    +DEBUG(dump(std::cerr));
    DOUT << ...;
    +DEBUG(dump(DOUT));
    std::cerr << "Hello world\n";
    llvm::cerr << "Hello world\n";
    std::cout << "Hello world\n";
    llvm::cout << "Hello world\n";
    std::cin >> Var;
    llvm::cin >> Var;
    std::ostream
    llvm::OStream
    std::istream
    llvm::IStream
    std::stringstream
    llvm::StringStream
    void print(std::ostream &Out);
    +// ...
    +print(std::cerr);
    void print(llvm::OStream Out);1
    +// ...
    +print(llvm::cerr);
    + +
    +
    + +
    +

    1llvm::OStream is a light-weight class so it should never +be passed by reference. This is important because in some configurations, +DOUT is an rvalue.

    +
    + +
    + +
    The Low Level Issues @@ -534,46 +623,70 @@ assert(isa<PHINode>(Succ->front()) && "Only works on PHId BBs!"

    You get the idea...

    +

    Please be aware when adding assert statements that not all compilers are aware of +the semantics of the assert. In some places, asserts are used to indicate a piece of +code that should not be reached. These are typically of the form:

    + +
    +
    +assert(0 && "Some helpful error message");
    +
    +
    + +

    When used in a function that returns a value, they should be followed with a return +statement and a comment indicating that this line is never reached. This will prevent +a compiler which is unable to deduce that the assert statement never returns from +generating a warning.

    + +
    +
    +assert(0 && "Some helpful error message");
    +// Not reached
    +return 0;
    +
    +
    +
    - Do not use 'using namespace std' + Do not use 'using namespace std'

    In LLVM, we prefer to explicitly prefix all identifiers from the standard -namespace with an "std::" prefix, rather than rely on "using namespace std;". -

    - -

    In header files, adding a 'using namespace XXX' directive pollutes the -namespace of any source file that includes the header. This is clearly a bad -thing.

    - -

    In implementation files (e.g. .cpp files) the rule is more of a stylistic -rule, but is still important. Basically, using explicit namespace prefixes -makes -the code more clear - because it is immediately obvious what facilities -are being used and where they are coming from - and more portable - -because namespace clashes cannot occur between LLVM code and other namespaces. -The portability rule is important because different standard library -implementations expose different symbols (potentially ones they shouldn't) and -future revisions to the C++ standard will add more symbols to the std -namespace. As such, we never 'using namespace std;' in LLVM.

    - -

    The exception to the general rule (i.e. it's not an exception for the std -namespace) is for implementation files. For example, all of the code in the -LLVM project implements code that lives in the 'llvm' namespace. As such, it -is ok, and actually more clear, for the .cpp files to have a 'using namespace -llvm' directive at their top, after the #includes. The general form of this -rule is that any .cpp file that implements code in any namespace may use that -namespace (and its parents), but should not use any others.

    +namespace with an "std::" prefix, rather than rely on +"using namespace std;".

    + +

    In header files, adding a 'using namespace XXX' directive pollutes +the namespace of any source file that includes the header. This is clearly a +bad thing.

    + +

    In implementation files (e.g. .cpp files), the rule is more of a stylistic +rule, but is still important. Basically, using explicit namespace prefixes +makes the code clearer, because it is immediately obvious what facilities +are being used and where they are coming from, and more portable, because +namespace clashes cannot occur between LLVM code and other namespaces. The +portability rule is important because different standard library implementations +expose different symbols (potentially ones they shouldn't), and future revisions +to the C++ standard will add more symbols to the std namespace. As +such, we never use 'using namespace std;' in LLVM.

    + +

    The exception to the general rule (i.e. it's not an exception for +the std namespace) is for implementation files. For example, all of +the code in the LLVM project implements code that lives in the 'llvm' namespace. +As such, it is ok, and actually clearer, for the .cpp files to have a 'using +namespace llvm' directive at their top, after the #includes. The +general form of this rule is that any .cpp file that implements code in any +namespace may use that namespace (and its parents'), but should not use any +others.

    - Provide a virtual method anchor for clases in headers + Provide a virtual method anchor for classes + in headers
    @@ -631,6 +744,7 @@ it's better to use a literal '\n'.

    +
    See Also @@ -644,15 +758,12 @@ sources. Two particularly important books for our work are:

      -
    1. Effective -C++ by Scott Meyers. There is an online version of the book (only some -chapters though) available as well. Also +
    2. Effective +C++ by Scott Meyers. Also interesting and useful are "More Effective C++" and "Effective STL" by the same author.
    3. -
    4. Large-Scale C++ -Software Design by John Lakos
    5. +
    6. Large-Scale C++ Software Design by John Lakos