home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 10 Tools / 10-Tools.zip / lifeos2.zip / LIFE-1.02 / EXAMPLES / SUPERLIN / SUPERLIN.LF < prev    next >
Text File  |  1996-06-04  |  34KB  |  189 lines

  1. module("superlint") ?
  2.  
  3. public(main) ?
  4.  
  5. D = getenv("SLDIR"), chdir(D) ?
  6.  
  7. load("c_public_terms")?
  8. load("sl_public_terms")?
  9. load("sl_utils")?
  10. load("sl_parser")?
  11.  
  12. open("c_public_terms")?
  13. open("sl_public_terms")?
  14. open("sl_parser")?
  15. open("sl_utils")?
  16. load("rl_overload")?
  17.  
  18. '*rule*'(_A: "variable_length",
  19.          _B,
  20.          _C) :- is_list_member("declaration",
  21.                                _C), (parse_mode :== prefix, _B :== local_declaration), !, '*rule_name*' <<- ref(_A), _D = _B .scope, _E = _D .left_brace, _F = _D .right_brace,(_E .file :\== _F .file, !, error_msg("Braces around a block must be in the same file",
  22.                                                                                                                                                                                                                      _F) ; strlen(_B .name .id) =< sqrt(_F .line - _E .line), !, error_msg("Variable name is too short",
  23.                                                                                                                                                                                                                                                                                            _B .name) ; succeed) ; succeed.
  24.  
  25. '*rule*'(_A: "extern_in_c_file",
  26.          _B,
  27.          _C) :- is_list_member("declaration",
  28.                                _C), (parse_mode :== prefix, _B :== external_declaration), !, '*rule_name*' <<- ref(_A),((_B .type .store_class :== extern, file_extension(_B .name .file) :== "c"), !, error_msg("No declaration in a .c file accessed out of the .c file",
  29.                                                                                                                                                                                                                  _B .name) ; succeed) ; succeed.
  30.  
  31. '*rule*'(_A: "block_alignment",
  32.          _B,
  33.          _C) :- is_list_member("alignment",
  34.                                _C), ((parse_mode :== prefix, is_not_token(_B)),((_B :== if, ! ; _B :== while), ! ; _B :== for)), !, '*rule_name*' <<- ref(_A), _D = _B,(_D :== {while;
  35.                                                                                                                                                                                 for}, !, _E = _B .keyword, _F = _B .body,(_F :== block, !, test_alignment(_E,
  36.                                                                                                                                                                                                                                                           _F) ; succeed) ; _D :== if, !, _G = _B .keyword, _H = _B .then_body, (_H :== block, !, test_alignment(_G,
  37.                                                                                                                                                                                                                                                                                                                                                                 _H) ; succeed), _I = _B .else_body,(_I :\== nothing, !, _J = _B .else_keyword,(_I :== block, !, test_alignment(_J,
  38.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                _I) ; succeed) ; succeed) ; succeed) ; succeed.
  39.  
  40. test_alignment(_A,
  41.                _B) :- _C = _B .left_brace, _D = _B .right_brace, (_C .white_spaces :\== " ", !, error_msg("There must be one space between brace and condition",
  42.                                                                                                           _C) ; succeed),(_D .column :\== _A .column, !, error_msg("Brace must be aligned with first character of instruction",
  43.                                                                                                                                                                    _D) ; succeed).
  44.  
  45. '*rule*'(_A: "nested_typedef",
  46.          _B,
  47.          _C) :- is_list_member("type_definition",
  48.                                _C), (parse_mode :== prefix, _B :== type_definition), !, '*rule_name*' <<- ref(_A), _D = _B .type,((_D :== protected_type, _D .type :== protected_type), !, error_msg("Only one level of nested parentheses allowed around type definitions",
  49.                                                                                                                                                                                                      _B .name) ; succeed) ; succeed.
  50.  
  51. '*rule*'(_A: "contiguous_nested_typedef",
  52.          _B,
  53.          _C) :- is_list_member("type_definition",
  54.                                _C), (parse_mode :== prefix, _B :== type_definition), !, '*rule_name*' <<- ref(_A), _D = _B .type,(((_D :== protected_type, _D .type :== protected_type), _D .left_parenthesis .next :== "("), !, error_msg("Only one level of contiguous nested parentheses allowed around type definitions",
  55.                                                                                                                                                                                                                                            _B .name) ; succeed) ; succeed.
  56.  
  57. '*rule*'(_A: "assignment_style",
  58.          _B,
  59.          _C) :- is_list_member("operator",
  60.                                _C), (parse_mode :== prefix, is_assignment_operator(_B)), !, '*rule_name*' <<- ref(_A),((_B .white_spaces :\== " ", ! ; _B .next .white_spaces :\== " "), !, error_msg("Assignment operators must be preceded and followed by a single space",
  61.                                                                                                                                                                                                       _B) ; succeed) ; succeed.
  62.  
  63. '*rule*'(_A: "adjacent_operators",
  64.          _B,
  65.          _C) :- is_list_member("operator",
  66.                                _C), ((parse_mode :== prefix, is_operator(_B)), is_token(_B)), !, '*rule_name*' <<- ref(_A),((is_operator(_B .previous), _B .white_spaces :== ""), !, error_msg("Two operators cannot be adjacent",
  67.                                                                                                                                                                                                _B) ; succeed) ; succeed.
  68.  
  69. '*rule*'(_A: "uninitialized_variable",
  70.          _B,
  71.          _C) :- is_list_member("semantics",
  72.                                _C), is_expression(_B), !, '*rule_name*' <<- ref(_A), _D = _B .mode, (parse_mode :== prefix, !, _E = _D,(_E :== special, !,(_B .operator :== "?", !, verify_init(_B .condition), verify_init(_B .then), verify_init(_B .else) ; _B :== protected_expression, !, verify_init(_B .expression) ; _B :== function_call, !, verify_init(_B .call), verify_init_args(_B .arguments .first_argument) ; _B :== array_reference, !, verify_init(_B .array), verify_init(_B .index) ; verify_init(_B .expression)) ; _E :== infix, !, _F = base_expression(_B .left_expression), ((_B .operator :== "=", _F :== identifier), !, set_feature(uninit_marked,
  73.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  true,
  74.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  _F) ; verify_init(_B .left_expression)), verify_init(_B .right_expression) ; _E :== {prefix;
  75.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                       postfix}, !, verify_init(_B .expression) ; succeed) ; succeed),(((parse_mode :== postfix, _D :== infix), _B .operator :== "="), !, _F = base_expression(_B .left_expression),(_F :== identifier, !, _G = declaration_of(_F .id),(_G :== local_declaration, !, set_initialized_variable(_F .id,
  76.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                              current_instruction .scope) ; succeed) ; succeed) ; succeed) ; succeed.
  77.  
  78. verify_init(_A) :- _A :== identifier, !,(has_feature(uninit_marked,
  79.                                                      _A), !, succeed ; _B = first_mention_of(_A .id),(_B :== nothing, !, error_msg("Variable may be uninitialized",
  80.                                                                                                                                    _A) ; succeed)) ; succeed.
  81.  
  82. verify_init_args(_A) :- _A :\== nothing, !, verify_init(_A .expression), verify_init_args(_A .next) ; succeed.
  83.  
  84. set_initialized_variable(_A,
  85.                          _B) :- _C = _B,(_C :== then_body, !, _D = _B .instruction, (has_feature(then_init_variables,
  86.                                                                                                  _D), !, succeed ; set_feature(then_init_variables,
  87.                                                                                                                                variables,
  88.                                                                                                                                _D)), set_feature(_A,
  89.                                                                                                                                                  init,
  90.                                                                                                                                                  _D .then_init_variables) ; _C :== else_body, !, _D = _B .instruction, (has_feature(else_init_variables,
  91.                                                                                                                                                                                                                                     _D), !, succeed ; set_feature(else_init_variables,
  92.                                                                                                                                                                                                                                                                   variables,
  93.                                                                                                                                                                                                                                                                   _D)), set_feature(_A,
  94.                                                                                                                                                                                                                                                                                     init,
  95.                                                                                                                                                                                                                                                                                     _D .else_init_variables) ; _C :== {for;
  96.                                                                                                                                                                                                                                                                                                                        {while;
  97.                                                                                                                                                                                                                                                                                                                         do_while}}, !, (has_feature(init_variables,
  98.                                                                                                                                                                                                                                                                                                                                                     _B), !, succeed ; set_feature(init_variables,
  99.                                                                                                                                                                                                                                                                                                                                                                                   variables,
  100.                                                                                                                                                                                                                                                                                                                                                                                   _B)), set_feature(_A,
  101.                                                                                                                                                                                                                                                                                                                                                                                                     init,
  102.                                                                                                                                                                                                                                                                                                                                                                                                     _B .init_variables) ; _C :== block, !, _E = _B .block_declarations .local_declarations,(has_feature(_A,
  103.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                         _E), !, set_feature(init,
  104.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                             true,
  105.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                             _E ._A) ; set_initialized_variable(_A,
  106.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                _B .scope)) ; _C :== {nothing;
  107.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      function_body}, !, succeed ; set_initialized_variable(_A,
  108.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            _B .scope) ; succeed).
  109.  
  110. '*rule*'(_A: "propagate_init",
  111.          _B,
  112.          _C) :- is_list_member("semantics",
  113.                                _C), ((_B :== if, is_not_token(_B)), parse_mode :== postfix), !, '*rule_name*' <<- ref(_A), _D = intersect_init_variables(_B), set_initialized_variables(_D,
  114.                                                                                                                                                                                         _B .scope) ; succeed.
  115.  
  116. set_initialized_variables(_A,
  117.                           _B) :- _A :== [], !, succeed ; set_initialized_variable(_A .first_element,
  118.                                                                                   _B), set_initialized_variables(_A .tail,
  119.                                                                                                                  _B).
  120.  
  121. intersect_init_variables(_A) -> _B | (has_feature(then_init_variables,
  122.                                                   _A), !,(has_feature(else_init_variables,
  123.                                                                       _A), !, _B = intersection(features_list(_A .then_init_variables),
  124.                                                                                                 features_list(_A .else_init_variables)) ; _B = features_list(_A .then_init_variables)) ; has_feature(else_init_variables,
  125.                                                                                                                                                                                                      _A), !, _B = features_list(_A .else_init_variables) ; _B = []), cond(_B :== @,
  126.                                                                                                                                                                                                                                                                           _B = unknown).
  127.  
  128. intersection(_A,
  129.              _B) -> _C | (_A :== [], !, _C = [] ; _D = _A .first_element, _E = intersection(_A .tail,
  130.                                                                                             _B),(member(_D,
  131.                                                                                                         _B), !, _C = newlist(_D,
  132.                                                                                                                              _E) ; _C = _E)), cond(_C :== @,
  133.                                                                                                                                                    _C = unknown).
  134.  
  135. base_expression(_A) -> _B | (_A :== protected_expression, !, _B = base_expression(_A .expression) ; _B = _A), cond(_B :== @,
  136.                                                                                                                    _B = unknown).
  137.  
  138. is_expression(_A) -> _B | (has_feature(mode,
  139.                                        _A), !, _B = true ; _B = false), cond(_B :== @,
  140.                                                                              _B = unknown).
  141.  
  142. first_mention_of(_A) -> _B | (current_block :== nothing, !, _B = external ; _B = search_mention_of(_A,
  143.                                                                                                    current_block)), cond(_B :== @,
  144.                                                                                                                          _B = unknown).
  145.  
  146. search_mention_of(_A,
  147.                   _B) -> _C | (_D = _B,(_D :== block, !, _E = _B .block_declarations .local_declarations,(has_feature(_A,
  148.                                                                                                                       _E), !,((_E ._A .initialization :\== nothing, ! ; has_feature(init,
  149.                                                                                                                                                                                     _E ._A)), !, _C = init ; _C = nothing) ; _C = search_mention_of(_A,
  150.                                                                                                                                                                                                                                                     _B .scope)) ; _D :== then_body, !, _F = _B .instruction,((has_feature(then_init_variables,
  151.                                                                                                                                                                                                                                                                                                                           _F), has_feature(_A,
  152.                                                                                                                                                                                                                                                                                                                                            _F .then_init_variables)), !, _C = init ; _C = search_mention_of(_A,
  153.                                                                                                                                                                                                                                                                                                                                                                                                             _F .scope)) ; _D :== else_body, !, _F = _B .instruction,((has_feature(else_init_variables,
  154.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   _F), has_feature(_A,
  155.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    _F .else_init_variables)), !, _C = init ; _C = search_mention_of(_A,
  156.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     _F .scope)) ; _D :== {for;
  157.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                           {while;
  158.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            do_while}}, !,((has_feature(init_variables,
  159.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        _B), has_feature(_A,
  160.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                         _B .init_variables)), !, _C = init ; _C = search_mention_of(_A,
  161.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     _B .scope)) ; _D :== {nothing;
  162.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                           function_body}, !, _C = external ; search_mention_of(_A,
  163.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                _B .scope) ; succeed)), cond(_C :== @,
  164.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                             _C = unknown).
  165.  
  166. declaration_of(_A) -> _B | (current_block :== nothing, !, _B = nothing ; _B = search_declaration(current_block .block_declarations,
  167.                                                                                                  _A)), cond(_B :== @,_B = unknown).
  168.  
  169. search_declaration(_A,
  170.                    _B) -> _C | ((_A :== block_declarations, !, _D = _A .local_declarations ; _D = nothing),(_D :== nothing, !, _C = nothing ; has_feature(_B,
  171.                                                                                                                                                           _D), !, _C = _D ._B ; _C = search_declaration(_A .parent_declarations,
  172.                                                                                                                                                                                                         _B))), cond(_C :== @,
  173.                                                                                                                                                                                                                     _C = unknown).
  174.  
  175. M : main :- 
  176.                   sl_parse(strip(M)),writeln, writeln("Style checking : "), writeln("----------------"), writeln, scan_tree({(operator, type_definition, alignment, declaration, variable_length)}), writeln, writeln("Uninitialized variables : "), writeln("-------------------------"), writeln, scan_tree(semantics).
  177.  
  178. '*superlint_rules*' <<- ["variable_length",
  179.  "extern_in_c_file",
  180.  "block_alignment",
  181.  "nested_typedef",
  182.  "contiguous_nested_typedef",
  183.  "assignment_style",
  184.  "adjacent_operators",
  185.  "uninitialized_variable",
  186.  "propagate_init",
  187.  "main"] ?
  188.  
  189.