1 | C/C++-Style guide for Singular |
---|
2 | ----------------------------- |
---|
3 | - C/C++ files - names (applies to headers as well) |
---|
4 | - each C++ file should have the extension .cc |
---|
5 | - each C file should have the extension .c |
---|
6 | - each header file should have the extension .h |
---|
7 | it should be possible to include it in C and C++ sources |
---|
8 | - converted to lower case, each file name must be unique in the |
---|
9 | first 8 characters |
---|
10 | - it is recommended to use only lower case file names |
---|
11 | |
---|
12 | - C/C++ files - structure |
---|
13 | - TODO: What about Copyright note? |
---|
14 | (Contained in COPYING unless otherwise specified). |
---|
15 | - each C/C++ file (abc.c/abc.cc/abc.h) should start with a short comment |
---|
16 | about its purpose in doxygen format (TODO: see file templates) giving |
---|
17 | at least the filename and a brief description of the contents. |
---|
18 | (Each header of a file should contain an Id/Rev field) |
---|
19 | TODO: should not contain CVS $Id: C-STYLEGUIDE,v 1.5 2009-06-05 11:01:19 Singular Exp $ tag!? |
---|
20 | - order "#include" statements from global to local scope: |
---|
21 | i. first: all system include files: |
---|
22 | #include <iostream>, #include <boost/shred_ptr.h> |
---|
23 | (remember to include optional include files in #ifdef ... #end) |
---|
24 | ii. only source files: #include "mod2.h" |
---|
25 | iii. at last: all other files (which you really need): |
---|
26 | #include "poly.h" etc. |
---|
27 | - paths in "#include" statements should be avoided (should be specified by |
---|
28 | build system level instead) |
---|
29 | |
---|
30 | - Header files |
---|
31 | - see C/C++ files - structure! |
---|
32 | - each header file abc.h should contain a multiple inclusions preventing |
---|
33 | mechanism as follows: |
---|
34 | |
---|
35 | #ifndef ABC_H |
---|
36 | #define ABC_H |
---|
37 | |
---|
38 | // .... declarations ... |
---|
39 | |
---|
40 | #endif // ABC_H |
---|
41 | |
---|
42 | - do NOT include mod2.h! |
---|
43 | - include only the header files you really need |
---|
44 | (use forward declarations wherever possible) |
---|
45 | - all declarations (macros, types, variables, enumerations, function |
---|
46 | parameters...) should be documented in doxygen format. Brief comments are |
---|
47 | mandatory, long comments are optional (TODO: see file templates) |
---|
48 | - class-/function-/member variable-/... comments should be written in the |
---|
49 | doxygen format (see Doxygen quick reference card) |
---|
50 | - further (non doxygen) comments can be used to separate the file into easily |
---|
51 | visible sections |
---|
52 | |
---|
53 | - format |
---|
54 | - general screen width: 80 columns |
---|
55 | - each procedure declarations should be in one line, if possible |
---|
56 | - the number of required function parameters should be as small as possible |
---|
57 | - curly braces: Matching curly brackets should be either vertically |
---|
58 | or horizontally aligned. |
---|
59 | - the "else" keyword indents the same as its matching "if" |
---|
60 | - indentation should be small |
---|
61 | (e.g. two positions (spaces) for each level of nesting) |
---|
62 | - avoid tabs: their interpretation differs from editor to editor. |
---|
63 | - use empty lines seldom: only to break up very long routines and between |
---|
64 | routines |
---|
65 | - avoid code copying/duplication |
---|
66 | - declare local variables as late as possible and with the smallest possible |
---|
67 | visibility scope |
---|
68 | - avoid using "goto", "continue", "break" statements |
---|
69 | (save for "switch/case" blocks and error handling) |
---|
70 | - compiler warnings should be enabled and regarded as errors |
---|
71 | - whenever possible, constants should be defined as "const variables" |
---|
72 | not via "#define". |
---|
73 | Non pure C++ parts must use #define. |
---|
74 | - Consider the choice between macros and inline function very careful, |
---|
75 | prefer inline functions: |
---|
76 | - macros are not type safe |
---|
77 | + macros are allways inlined |
---|
78 | - arguments to macros can be multiply computed |
---|
79 | |
---|
80 | - "inline" is only a hint for the optimizer (especially in the C parts): |
---|
81 | in non-optimzed code these functions are NOT inlined. |
---|
82 | -/+ inline functions are not generic (requires the defined types) |
---|
83 | |
---|
84 | - Naming conventions: |
---|
85 | - All code and global variables must conform to this naming convention, |
---|
86 | it does not apply to local variables. |
---|
87 | - the names consists of a short (small letter) prefix, |
---|
88 | the first letter of each following word is capitalized |
---|
89 | (The routines Werror/WerrorS/Warn/WarnS/Print/PrintS have an empty prefix) |
---|
90 | - the prefix describes the area the name belongs to: |
---|
91 | p: polynomial operations |
---|
92 | n/np/nl/na/: number operations (general/Zp/Q/alg.ext.) |
---|
93 | k: std engine |
---|
94 | ... |
---|
95 | - _ (underscore) is only used as a last part of the prefix: |
---|
96 | (example: p_Add): the last argument is the base ring |
---|
97 | - macros are in capital letters (except used as a procedure) |
---|
98 | |
---|
99 | - Comments |
---|
100 | - class-/function-/member variable-/... comments should be written in the |
---|
101 | doxygen format (see Doxygen quick reference card) |
---|
102 | - documentation should explain the purpose of each type/function/parameter/., |
---|
103 | as well as its return value or any preconditions/side effects if applicable |
---|
104 | - comments in source files about implementation details need not be in |
---|
105 | doxygen format |
---|
106 | - do not comment on trivial matters. Implementation details should be |
---|
107 | sufficiently commented for others to understand the inner workings of the |
---|
108 | code. |
---|
109 | - document difficult algorithms by a reference to an article/book/etc. |
---|
110 | |
---|
111 | - Checks / Debugging aids |
---|
112 | - interpreter routines have to check their input |
---|
113 | - use const wherever possible/suitable (especially in declarations of input |
---|
114 | parameters to functions/methods provided as pointers or references or for |
---|
115 | methods that do not change the state of an object, consider delaring |
---|
116 | variables "mutable" whenever suitable) |
---|
117 | |
---|
118 | - kernel routines have to document their requirements, |
---|
119 | the checks have to be done in the interpreter. |
---|
120 | Repeat the checks only within #ifndef NDEBUG/#endif |
---|
121 | or via assert. |
---|
122 | - input should be checked to conform with the documentation via assume |
---|
123 | (if this is simple) |
---|
124 | - more time consuming tests should be within |
---|
125 | #ifdef PDEBUG/#ifdef KDEBUG/#ifdef LDEBUG |
---|
126 | (see mod2.h) |
---|
127 | - case statements (or equivalent if/else constructs) |
---|
128 | should always have an default entry |
---|
129 | (maybe an error message) |
---|
130 | |
---|
131 | - C++ features |
---|
132 | - to avoid confusion: "struct" should be a C object, |
---|
133 | if you really need C++ extensions, use "class". |
---|
134 | - "and"/"or"/"not" are not recognized by all compilers, use &&, &, ||, |, ! |
---|
135 | - TODO: What about namespaces!? |
---|
136 | |
---|