l_misc.c 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155
  1. /*
  2. * (c) copyright 1987 by the Vrije Universiteit, Amsterdam, The Netherlands.
  3. * See the copyright notice in the ACK home directory, in the file "Copyright".
  4. */
  5. /* $Header$ */
  6. /* Lint miscellaneous routines */
  7. #include "lint.h"
  8. #ifdef LINT
  9. #include <alloc.h> /* for st_free */
  10. #include "arith.h" /* definition arith */
  11. #include "label.h" /* definition label */
  12. #include "expr.h"
  13. #include "idf.h"
  14. #include "def.h"
  15. #include "code.h" /* RVAL etc */
  16. #include "LLlex.h"
  17. #include "Lpars.h"
  18. #include "stack.h"
  19. #include "type.h"
  20. #include "level.h"
  21. #include "nofloat.h"
  22. #include "l_state.h"
  23. extern char *symbol2str();
  24. extern struct type *func_type;
  25. lint_conversion(oper, from_type, to_type)
  26. struct type *from_type, *to_type;
  27. {
  28. register int from = from_type->tp_fund;
  29. register int to = to_type->tp_fund;
  30. switch (oper) {
  31. case RETURN: /* not really an oper, but it works */
  32. case INT2INT:
  33. case '=':
  34. case PLUSAB:
  35. case MINAB:
  36. case TIMESAB:
  37. case DIVAB:
  38. case MODAB:
  39. case LEFTAB:
  40. case RIGHTAB:
  41. case ANDAB:
  42. case XORAB:
  43. case ORAB:
  44. if ( (from == LONG && to != LONG)
  45. || (from == DOUBLE && to != DOUBLE)
  46. ) {
  47. awarning("conversion from %s to %s may lose accuracy",
  48. symbol2str(from), symbol2str(to));
  49. }
  50. }
  51. }
  52. lint_ret_conv(from_type)
  53. struct type *from_type;
  54. {
  55. lint_conversion(RETURN, from_type, func_type);
  56. }
  57. lint_ptr_conv(from, to)
  58. short from, to;
  59. {
  60. /* X -> X ok -- this includes struct -> struct, of any size
  61. * X -> CHAR ok
  62. * DOUBLE -> X ok
  63. * FLOAT -> LONG -> INT -> SHORT ok
  64. */
  65. if (from == to)
  66. return;
  67. if (to == CHAR)
  68. return;
  69. if (from == DOUBLE)
  70. return;
  71. switch (from) {
  72. case FLOAT:
  73. switch (to) {
  74. case LONG:
  75. case INT:
  76. case SHORT:
  77. return;
  78. }
  79. break;
  80. case LONG:
  81. switch (to) {
  82. case INT:
  83. case SHORT:
  84. return;
  85. }
  86. break;
  87. case INT:
  88. switch (to) {
  89. case SHORT:
  90. return;
  91. }
  92. break;
  93. }
  94. if (from == CHAR) {
  95. hwarning("pointer to char may not align correctly for a %s",
  96. symbol2str(to));
  97. }
  98. else {
  99. warning("pointer to %s may not align correctly for a %s",
  100. symbol2str(from), symbol2str(to));
  101. }
  102. }
  103. lint_relop(left, right, oper)
  104. struct expr *left, *right;
  105. int oper; /* '<', '>', LESSEQ, GREATEREQ, EQUAL, NOTEQUAL */
  106. {
  107. /* <unsigned> <relop> <neg-const|0> is doubtful */
  108. if ( left->ex_type->tp_unsigned
  109. && right->ex_class == Value
  110. && right->VL_CLASS == Const
  111. ) {
  112. if (right->VL_VALUE < 0) {
  113. warning("unsigned compared to negative constant");
  114. }
  115. if (right->VL_VALUE == 0) {
  116. switch (oper) {
  117. case '<':
  118. warning("unsigned < 0 will always fail");
  119. break;
  120. case LESSEQ:
  121. warning("unsigned <= 0 is probably wrong");
  122. break;
  123. case GREATEREQ:
  124. warning("unsigned >= 0 will always succeed");
  125. break;
  126. }
  127. }
  128. }
  129. /* <char> <relop> <neg-const> is undefined */
  130. if ( left->ex_type->tp_fund == CHAR
  131. && right->ex_class == Value
  132. && right->VL_CLASS == Const
  133. && (right->VL_VALUE < 0 || right->VL_VALUE > 127)
  134. ) {
  135. warning("character compared to negative constant");
  136. }
  137. }
  138. #endif LINT