position.c 3.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134
  1. /* $Id$ */
  2. #include <stdio.h>
  3. #include <assert.h>
  4. #include <alloc.h>
  5. #include <out.h>
  6. #include <stb.h>
  7. #include "position.h"
  8. #include "scope.h"
  9. #include "file.h"
  10. #include "idf.h"
  11. #include "symbol.h"
  12. #include "misc.h"
  13. extern FILE *db_out;
  14. static struct outname *f_start, *f_end;
  15. /* extern p_position get_position_from_addr(t_addr t);
  16. Returns a pointer to a structure containing the source position of the code
  17. at address 't'. 0 is returned if no source position could be found.
  18. */
  19. p_position
  20. get_position_from_addr(t)
  21. t_addr t;
  22. {
  23. static t_position retval;
  24. register struct outname *p;
  25. register int i,j;
  26. if (! f_start) return 0;
  27. i = 0;
  28. j = f_end - f_start;
  29. do {
  30. p = &f_start[((i + j) >> 1) + ((i + j) & 1)];
  31. while ((p->on_type >> 8) != N_SLINE) p++;
  32. if (p->on_valu > t) {
  33. p--;
  34. while (p > &f_start[i] && (p->on_type >> 8) != N_SLINE) p--;
  35. j = p-f_start;
  36. }
  37. else i = p-f_start;
  38. } while (i < j);
  39. retval.lineno = f_start[j].on_desc;
  40. p = &f_start[j-1];
  41. while ((i = p->on_type >> 8) != N_SOL && i != N_SO) p--;
  42. retval.filename = p->on_mptr;
  43. return &retval;
  44. }
  45. /* extern t_addr get_addr_from_position(p_position p);
  46. Returns the address of the code at position 'p', or ILL_ADDR if it could
  47. not be found. If there is no symbolic information for the filename in
  48. position 'p', an error message will be given.
  49. */
  50. t_addr
  51. get_addr_from_position(p)
  52. p_position p;
  53. {
  54. register p_symbol sym = Lookup(findidf(p->filename), PervasiveScope, FILESYM);
  55. if (sym) {
  56. register unsigned int i;
  57. register p_file map = sym->sy_file;
  58. for (i = p->lineno; i > 0; i--) {
  59. register struct outname *n = map->f_line_addr[HASH(i)];
  60. while (n) {
  61. if (n->on_desc == i) return (t_addr) n->on_valu;
  62. n = next_outname(n);
  63. }
  64. }
  65. return ILL_ADDR;
  66. }
  67. error("no symbolic information for file %s", p->filename);
  68. return ILL_ADDR;
  69. }
  70. /* extern add_position_addr(char *filename, struct outname *n);
  71. Adds the ('filename','lineno'),'t' pair to the mapping information.
  72. */
  73. add_position_addr(filename, n)
  74. char *filename;
  75. register struct outname *n;
  76. {
  77. static char *lastfile = 0;
  78. static p_file lastmap = 0;
  79. register p_file map = lastmap;
  80. if (filename != lastfile) { /* new file ... */
  81. register p_symbol sym;
  82. lastfile = filename;
  83. if (! filename) { /* last call */
  84. return;
  85. }
  86. sym = Lookup(findidf(filename), PervasiveScope, FILESYM);
  87. if (sym) map = sym->sy_file;
  88. else {
  89. sym = add_file(filename);
  90. map = sym->sy_file;
  91. map->f_scope = FileScope;
  92. }
  93. lastmap = map;
  94. if (! f_start) f_start = n;
  95. }
  96. else map = lastmap;
  97. if (map) {
  98. f_end = n;
  99. setnext_outname(n, map->f_line_addr[HASH(n->on_desc)]);
  100. map->f_line_addr[HASH(n->on_desc)] = n;
  101. }
  102. }
  103. /* extern p_position print_position(t_addr a, int print_function);
  104. Prints position 'a' and returns it. If 'print_function' is set,
  105. an attempt is made to print the function name as well.
  106. */
  107. p_position
  108. print_position(a, print_function)
  109. t_addr a;
  110. int print_function;
  111. {
  112. register p_position pos = get_position_from_addr(a);
  113. if (print_function) {
  114. register p_scope sc = base_scope(get_scope_from_addr(a));
  115. if (sc) fprintf(db_out, "in %s ", sc->sc_definedby->sy_idf->id_text);
  116. }
  117. if (pos) fprintf(db_out, "at \"%s\":%u", pos->filename, pos->lineno);
  118. return pos;
  119. }