embedded software boot camp

How to Enforce Coding Standards Using PC-Lint

Thursday, June 16th, 2011 by Michael Barr

In an earlier blog post, I introduced the concept of automatic enforcement of coding standards by stating that:

Enforcement of coding standards too often depends on programmers already under deadline pressure to be disciplined while they code and/or to make time to perform peer code reviews. … To ensure your selected coding standard is followed, and thus effective, your team should find as many automated ways to enforce as many of its rules as possible. And you should make such automated rule checking part of the everyday software build process.

One of the tools we have found to be indispensible for this purpose is Gimpel Software‘s PC-Lint (and the multi-platform FlexeLint). At just a few hundred dollars per seat, PC-Lint happens to also be one of the least expensive tools we own and thus a source of tremendous value to our team.

The following options can be set (in version 9.00) to assist in the automated enforcement of the identified rules from Barr Group’s Embedded C Coding Standard.

 

Rule(s) Tool Configuration Notes
Which C (1.1) 975 (unrecognized pragma)

+pragma(name, action)

-pragma(name)

Braces (1.3) PC-Lint can help identify missing braces through indentation checking:

525 (negative indentation)

539 (did not expect positive indentation)

725 (expected positive indentation)

Parentheses (1.4) 665 (Unparenthesized parameter in macro is passed an expression)

773 (Expression-like macro not parenthesized)

821 (Right hand side of assignment not parenthesized)

834 (Operator ‘Name’ followed by operator ‘Name’ is confusing. Use parentheses)

973 (Unary operator in macro ‘Symbol‘ not parenthesized)

Casts (1.6) 507, 511, 519 (Size incompatibility in cast)

549, 571, 611 (suspicious cast)

643 (loss of precision in pointer cast)

680 (suspicious truncation in arithmetic expression converted to pointer)

688 (cast used within preprocessor conditional statement)

740, 741 (unusual pointer cast)

920 (cast from ‘type’ to ‘void’)

921-930 (cast from ‘type’ to ‘type’)

1773 (attempt to cast away const or volatile)

Keywords to avoid (1.7) -deprecate( keyword, auto, violates coding standard )

-deprecate( keyword, register, violates coding standard )

-deprecate( keyword, goto, violates coding standard )

-deprecate( keyword, continue, violates coding standard )

Keywords to Frequent (1.8) 818 (Pointer parameter could be declared ptr to const)

843 (Variable could be declared as const)

844 (Pointer variable could be declared as const)

952 (parameter could be declared as const)

953 (variable could be declared as const)

954 (pointer variable could be declared as pointing to a const)

765 (external symbol could be made static)

Comments, Acceptable Formats (2.1) 602 (comment within comment)
Alignment (3.2)

Indentation (3.4)

525 (negative indentation)

539 (did not expect positive indentation)

725 (expected positive indentation)

Header Files (4.2)

Source Files (4.3)

451 (header file repeatedly included but does not have a standard include guard)

766 (Include of header file not used in module)

966 (indirectly included header file not used in module)

967 (Header file does not have a standard include guard)

Fixed Width Integers (5.2)

Signed Integers (5.3)

569 (Loss of information — Integer bits to Integer bits)

570 (loss of sign, assignment being made from a negative constant to an unsigned quantity)

573 (signed-unsigned mix with divide)

574 (signed-unsigned mix with relational)

701, 703 (shift left of signed quantity)

702, 704 (shift right of signed quantity)

712 (loss of precision, one type is larger than another type)

713 (loss of precision, signed to unsigned)

734 (loss of precision, to a quantity smaller than an int)

Structure and Unions (5.5) 38 (Offset of symbol inconsistent — A member of a class or struct appears in a different position (offset from the start of the structure) than an earlier declaration)

39 (Redefinition of symbol conflicts with ‘location’ — a struct or a union is being redefined)

Function-Like Macros (6.3) 665 (Unparenthesized parameter in macro is passed an expression)

773 (Expression-like macro not parenthesized)

Initialization (7.2) 35 (initializer has side-effects)

133 (too many initializers for aggregate)

134 (missing initializer)

530, 603 (symbol not initialized)

540 (excessive size — a string initializer required more space than what was allocated)

644 (variable may not have been initialized)

651 (potentially confusing initializer)

708 (union initialization)

727, 728, 729, 738 (symbol not explicitly initialized)

771, 772 (symbol conceivably not initialized)

784 (nul character truncated from string — During initialization of an array with a string constant there was not enough room to hold the trailing NUL character)

785, 943 (too few initializers for aggregate)

940 (omitted braces within an initializer)

Switch Statements (8.3) 44 (A case or default statement occurred outside a switch)

108 (Invalid context — A continue or break statement was encountered without an appropriate surrounding context)

137 (constant used twice within switch)

408 (type mismatch with switch expression)

744 (switch statement has no default)

764 (switch statement does not have a case)

825 (control flows into case/default)

Equivalence Tests (8.6) 720 (Boolean test of assignment)

 

As a convenience to readers who follow Barr Group’s Embedded C Coding Standard and may like to use RSM and/or PC-Lint to inexpensively and automatically enforce as many of the rules as possible, here are starter configuration files:

Tags: , , ,

10 Responses to “How to Enforce Coding Standards Using PC-Lint”

  1. Dennis says:

    Hello Micheal,

    Reading this post a question popped up in my mind.
    How do you handle third party libraries? As you cannot run LINT over that (or any other automated tool).

    How do you guaranty that part of the firmware is bug free?

    Regards,
    Dennis

  2. Fernando says:

    I´m not an expert, but it´s suposed that you pay for code that has been tested and that has a certain quality level.
    If you are paying for a library that you suspect it may contain bugs, then change your third party provider.

    Best regards,
    Fernando

  3. Tomaz says:

    Hello Michael,
    very interesting article. To use automated tools to force one to make better code is very tempting. Can you make some comment on integration of proposed method into IAR environment as PC-lint already can be integrated.
    Regards,
    Tomaz

    • Tim says:

      If you have an older version of IAR you should check out this technote: http://supp.iar.com/Support/?note=42513&from=search+result

      Unfortunately it does not work on the latest 6.xx version. I too would like to better understand what needs to go into setting up the environment. I haven’t had a lot of time to mess around with the configurations. It appears to me that it is mostly a matter of entering the #defined objects from IAR into the PC-lint config file, but there is probably more to it than that.

  4. Michael Barr says:

    There is now an official version of this file (including refinements suggested by the publishers of PC-Lint) on the Gimpel Software website at http://www.gimpel.com/html/pub90/au-netrino.lnt

  5. Chris Hills says:

    IAR are currently (Sept 2011) working on PC-lint intergration for EWARM V6.***

    I did the orignal EW-C-lint intergration document on their web site. (also one for Keil, Borland and Code Warrior)

    PC-lint can also enforce MISRA-C 98, 04 and hopfully 12 (Also MISRA-C++)

    Whilst there are more powerfull Static analysers than PC-Lint (also with more features like metrics, graphical dfront ends, deeper analysis etc) PC-lint is the best “bang per buck” tool there is. There is no credibile argument for anyone using C not to be doing static analysis.

  6. Tomaz says:

    Hello Chris,
    can you tell, if and when integration of PC-Lint and EWARM v6.x will be done?
    Regards,
    Tomaz

    • Tim says:

      It appears there is now support for EWARM v6.xx:

      http://supp.iar.com/Support/?note=21805

      I’ve gotten it working on my setup.

      • Tomaz says:

        Thank You Tim,
        I also noticed this few days ago. I have now PC-Lint integrated in IAR together with Netrino options. I also included RSM as external tool in IAR, although I cannot get links to source code in its output. Does anybody have any suggestions for this. RSM can format its output in Visual Studio format, is this of any help?

      • Bill says:

        I followed the latest IAR Technote (TN-21805) on my Win7 setup and found two discrepancies: 1) Once you generate the predefined macros (Step 2B of the TN) you should mark that file “Read Only” so that it isn’t removed when you do a Project->Clean; 2) The path to the libraries in the “iar-co’arm-v6.lnt” file is incorrect (at least as it was installed on my system. The .lnt file comes with “C:\Program…\Embedded Workbench ARM 6.30.1\arm\…” but should be “C:\Program…\Embedded Workbench 6.0\arm\…”

Leave a Reply to Tim