Each directory here represents an assembly, and inside each directory we
divide the code based on the namespace they implement.
+In addition, each assembly directory contains a Test directory that holds the
+NUnit tests for that assembly.
+
+We use a new build system which is described by various README files
+in mcs/build
+
+The build process typically builds an assembly, but in some cases it
+also builds special versions of the assemblies intended to be used for
+testing.
+
* Missing implementation bits
If you implement a class and you are missing implementation bits,
- please put in the code the word "TODO" and a description of what
- is missing to be implemented.
+ please use the attribute [MonoTODO]. This attribute can be used
+ to programatically generate our status web pages:
+
+ [MonoTODO]
+ int MyFunction ()
+ {
+ throw new NotImplementedException ();
+ }
+
+* Supporting .NET 1.2, .NET 1.1 and .NET 1.0 builds
+
+ The defines NET_1_1 and NET_2_0 are used to include
+ features. When NET_2_0 is defined, it also implies that the
+ NET_1_1 is defined.
+
+ To have code which is only available in an old version, use ONLY_1_0,
+ ONLY_1_1
* Tagging buggy code
Do not use XXX or obscure descriptions, because otherwise people
will not be able to understand what you mean.
-* Coding consideration
+* Tagging Problematic specs.
+
+ If the documentation and the Microsoft implementation do
+ differ (you wrote a test case to prove this), I suggest that you edit
+ the file `mcs/class/doc/API-notes' so we can keep track of these problems
+ and submit our comments to ECMA or Microsoft and seek clarification.
+
+ Sometimes the documentation might be buggy, and sometimes the implementation
+ might be buggy. Lets try to identify and pinpoint which one
+ is the correct one.
+
+ Sometimes the specification will be lame (consider Version.ToString (fieldCount)
+ where there is no way of knowing how many fields are available, making the API
+ not only stupid, but leading to unreliable code).
+
+ In those cases, use the keyword "LAMESPEC".
+
+
+* Coding considerations and style.
+
+ In order to keep the code consistent, please use the following
+ conventions. From here on `good' and `bad' are used to attribute
+ things that would make the coding style match, or not match. It is not
+ a judgement call on your coding abilities, but more of a style and
+ look call. Please try to follow these guidelines to ensure prettiness.
Use 8 space tabs for writing your code (hopefully we can keep
this consistent). If you are modifying someone else's code, try
to keep the coding style similar.
+ Since we are using 8-space tabs, you might want to consider the Linus
+ Torvals trick to reduce code nesting. Many times in a loop, you will
+ find yourself doing a test, and if the test is true, you will nest.
+ Many times this can be changed. Example:
+
+
+ for (i = 0; i < 10; i++) {
+ if (something (i)) {
+ do_more ();
+ }
+ }
+
+ This take precious space, instead write it like this:
+
+ for (i = 0; i < 10; i++) {
+ if (!something (i))
+ continue;
+ do_more ();
+ }
+
+ A few guidelines:
+
+ * Use a space before an opening parenthesis when calling
+ functions, or indexing, like this:
+
+ method (a);
+ b [10];
+
+ * Do not put a space after the opening parenthesis and the
+ closing one, ie:
+
+ good: method (a); array [10];
+
+ bad: method ( a ); array[ 10 ];
+
+ * Inside a code block, put the opening brace on the same line
+ as the statement:
+
+ good:
+ if (a) {
+ code ();
+ code ();
+ }
+
+ bad:
+ if (a)
+ {
+ code ();
+ code ();
+ }
+
+ * Avoid using unecessary open/close braces, vertical space
+ is usually limited:
+
+ good:
+ if (a)
+ code ();
+
+ bad:
+ if (a) {
+ code ();
+ }
+
+ * When defining a method, use the C style for brace placement,
+ that means, use a new line for the brace, like this:
+
+ good:
+ void Method ()
+ {
+ }
+
+ bad:
+ void Method () {
+ }
+
+ * Properties and indexers are an exception, keep the
+ brace on the same line as the property declaration.
+ Rationale: this makes it visually
+ simple to distinguish them.
+
+ good:
+ int Property {
+ get {
+ return value;
+ }
+ }
+
+ bad:
+ int Property
+ {
+ get {
+ return value;
+ }
+ }
+
+ Notice how the accessor "get" also keeps its brace on the same
+ line.
+
+ For very small properties, you can compress things:
+
+ ok:
+ int Property {
+ get { return value; }
+ set { x = value; }
+ }
+
+ * Use white space in expressions liberally, except in the presence
+ of parenthesis:
+
+ good:
+
+ if (a + 5 > method (blah () + 4))
+
+ bad:
+ if (a+5>method(blah()+4))
+
+ * For any new files, please use a descriptive introduction, like
+ this:
+
+ //
+ // System.Comment.cs: Handles comments in System files.
+ //
+ // Author:
+ // Juan Perez (juan@address.com)
+ //
+ // (C) 2002 Address, Inc (http://www.address.com)
+ //
+
+ * If you are modyfing someone else's code, and your contribution
+ is significant, please add yourself to the Authors list.
+
+ * Switch statements have the case at the same indentation as the
+ switch:
+
+ switch (x) {
+ case 'a':
+ ...
+ case 'b':
+ ...
+ }
+
+ * Argument names should use the camel casing for
+ identifiers, like this:
+
+ good:
+ void Method (string myArgument)
+
+ bad:
+ void Method (string lpstrArgument)
+ void Method (string my_string)
+
+ * Empty methods: They should have the body of code using two
+ lines, in consistency with the rest:
+
+ good:
+ void EmptyMethod ()
+ {
+ }
+
+ bad:
+ void EmptyMethod () {}
+
+ void EmptyMethod ()
+ {}
+
+ * Line length: The line length for C# source code is 134 columns.
+
+
+ If your function declaration arguments go beyond
+ this point, please align your arguments to match the
+ opening brace, like this:
+
+ void Function (int arg, string argb,
+ int argc)
+ {
+ }
+
+ When invoking functions, the rule is different, the
+ arguments are not aligned with the previous
+ argument, instead they begin at the tabbed position,
+ like this:
+
+ void M ()
+ {
+ MethodCall ("Very long string that will force",
+ "Next argument on the 8-tab pos",
+ "Just like this one")
+
+ }
+
+ Here are a couple of examples:
+
+class X : Y {
+
+ bool Method (int argument_1, int argument_2)
+ {
+ if (argument_1 == argument_2)
+ throw new Exception (Locale.GetText ("They are equal!");
+
+ if (argument_1 < argument_2) {
+ if (argument_1 * 3 > 4)
+ return true;
+ else
+ return false;
+ }
+
+ //
+ // This sample helps keep your sanity while using 8-spaces for tabs
+ //
+ VeryLongIdentifierWhichTakesManyArguments (
+ Argument1, Argument2, Argument3,
+ NestedCallHere (
+ MoreNested));
+ }
+
+ bool MyProperty {
+ get {
+ return x;
+ }
+
+ set {
+ x = value;
+ }
+ }
+
+ void AnotherMethod ()
+ {
+ if ((a + 5) != 4) {
+ }
+
+ while (blah) {
+ if (a)
+ continue;
+ b++;
+ }
+ }
+}
+