/*
 * $Id: codestyl.txt 13267 2009-12-16 17:38:13Z vszakats $
 */

/* Please note the following comments we may use everywhere
   NOTE: Notes
   TODO: something should be added here
   TOFIX: something needs to be fixed
   OBSOLETE: something could be removed from here
   QUESTION: I had some questions at this point but I could not get an answer
   OPT: something is commented out to improve performance
   As an example: */

Harbour Coding Standards
========================
(based heavily on coding standards placed in PHP)


Code Implementation
-------------------

[0] Document your code in source files and the manual. [tm]

[1] Functions that are given pointers to resources should not free them

  For instance, function int mail(char *to, char *from) should NOT free
  to and/or from.
  Exceptions:

  - The function's designated behavior is freeing that resource.
    E.g. hb_xfree()
  - The function is given a boolean argument, that controls whether or not
    the function may free its arguments (if true - the function must free its
    arguments, if false - it must not)

[2] Functions that are tightly integrated with other functions within the
    same module, and rely on each other non-trivial behavior, should be
    documented as such and declared 'static'.  They should be avoided if
    possible.

[3] Use definitions and macros whenever possible, so that constants have
    meaningful names and can be easily manipulated.
    Use TRUE instead of 1 (in boolean context)
    Use FALSE instead of 0 (in boolean context)
    Use NULL instead of 0 (in pointer context)
    Always use 'HB_' prefix for definitions of new datatypes and macros.
    Use either 'PHB_' prefix for datatypes that are pointers.

    e.g.
    HB_ITEM
    PHB_ITEM

[4] When writing functions that deal with strings, be sure to remember
    that Harbour holds the length property of each string, and that it
    shouldn't be calculated with strlen().  Write your functions in a such
    a way so that they'll take advantage of the length property, both
    for efficiency and in order for them to be binary-safe.
    Functions that change strings and obtain their new lengths while
    doing so, should return that new length, so it doesn't have to be
    recalculated with strlen()

[5] NEVER USE strncat().  If you're absolutely sure you know what you're doing,
    check its man page again, and only then, consider using it, and even then,
    try avoiding it.


[6] Use assert(). Not only does good assertion catch bugs, but it also
    helps with code readability.
     - Do not use assert for error handling. Use assert only for the
       condition that must be always true.
     - Do not use assignments in assert conditions.  If you assign inside an
       assert condition, you risk an elusive bug that would be very difficult
       to spot in a debug build, due to the side effect of the assignment.
       Function calls in assert conditions may also cause this problem, if
       they modify one of their arguments or global variables.

[7] When commenting out code using a #if statement, do NOT use 0 only. Instead
    use "<cvs username here>_0". For example, #if FOO_0, where FOO is your
    cvs user foo.  This allows easier tracking of why code was commented out,
    especially in bundled libraries.


[8] Use  hb_xgrab()/hb_xalloc(), hb_xfree(), hb_xrealloc(), hb_xsize() to
    manage memory allocations. These functions implement an internal
    "safety-net" mechanism that ensures the deallocation of any unfreed
    memory at the end of an application.  They also provide useful
    allocation and overflow information while running in debug mode.

Naming Conventions
------------------

[1] Function names for user-level functions defined in C code should be
    enclosed with in the HB_FUNC() macro. They should be in uppercase.
    The name should be prefixed with 'HB_' if this function is an
    extension to functions set defined in Clipper
    Abbreviations should not be used when they greatly decrease the
    readability of the function name itself.

[2] Variable names must be meaningful. One letter variable names must be
    avoided, except for places where the variable has no real meaning or
    a trivial meaning (e.g. for (i=0; i<100; i++) ...).

[3] Variable names should use so-called Hungarian notation. Use lowercase
    letters however use underscores to separate between words.

    Good:
    pMemoryPtr

    Bad:
    p_memory_ptr

[4] Static variables should be prefixed with 's_'

[5] Global variables (variables shared beetwen modules) should be
    prefixed with 'hb_<module_prefix>', e.g. hb_vm_bDebug, hb_gc_pStart


Syntax and indentation
----------------------

[1] Never use C++ style comments (i.e. // comment).  Always use C-style
    comments instead.  Harbour is written in C, and is aimed at compiling
    under any ANSI-C compliant compiler.  Even though many compilers
    accept C++-style comments in C code, you have to ensure that your
    code would compile with other compilers as well.

[2] Don't use K&R-style.  Of course, we can't and don't want to
    force anybody to use a style he or she is not used to, but,
    at the very least, when you write code that goes into the core
    of Harbour or one of its standard modules, please don't use the K&R
    style.  This applies to just about everything, starting with
    indentation and comment styles and up to function declaration
    syntax.

    (see also http://www.tuxedo.org/~esr/jargon/html/entry/indent-style.html)

[3] Be generous with whitespace and braces.  Always prefer:

    if( foo )
    {
       bar;
    }

    to:

    if(foo)bar;

    and to:

    if( foo ){
       bar;
    }

    Keep one empty line between the variable declaration section and
    the statements in a block, as well as between logical statement
    groups in a block.  Maintain at least one empty line between
    two functions.

[4] When indenting, use three spaces. It is important to maintain
    consistency in indenture so that definitions, comments, and
    control structures line up correctly.


Documentation
--------------

[1] Whenever be possible document yourself functions you developed.
    Usually it's hard to understand code written by other person, moreover
    when it involves some obscure algorithm, system's vars or attributes
    or data unavailable for the documentator.
    This is particularly evident for low level functions.

[2] After some time function was written, work becomes more difficult because
    it's needed to read the code several times (even for the own developer).
    This is evident when variables don't have useful names (and uses only
    letters).
    Because that, please DO NOT leave functions without documentation.

[3] If function made calls to other non-documented functions, and the
    original developer are not available anymore, could be so hard and even
    impossible to document it.

[4] Tracking which functions are documented and which are not, and if they
    are total or partially documented are a waste of resources in time and
    people.

[5] If you are the developer of the function don't worry by your narrative
    skills, concentrate in what functions do, which arguments it gets,
    which are its purpose and specially what information function returns.

[6] If you are the developer of the function, and you are using system's
    functions or vars undocumented, please explain it as much as possible.
    If you use a obscure or strange algorithm (i.e md5 ) please explain what
    it does and how it works.

[7] Notes, remarks and explainings enclose always between the /* */ pair,
    please don't use the double bar // because it difficults portability.

[8] Remember... documentation it's a much time consuming work, usually
    takes more time writing the documentation of a function that writing
    the function itself.
