1 /* Copyright (c) 1982 Regents of the University of California */
2 
3 static char sccsid[] = "@(#)address.c 1.1 01/18/82";
4 
5 /*
6  * Some machine and runtime dependent manipulation of a symbol.
7  */
8 
9 #include "defs.h"
10 #include "runtime.h"
11 #include "sym.h"
12 #include "machine.h"
13 #include "process.h"
14 #include "object.h"
15 #include "mappings.h"
16 #include "sym/classes.h"
17 #include "frame.rep"
18 #include "sym/sym.rep"
19 
20 /*
21  * Calculate the address of a symbol.
22  * If frame is not NIL, then it is the frame associated with the
23  * activation in which the symbol we're interested in is defined.
24  */
25 
26 ADDRESS address(s, frame)
27 register SYM *s;
28 FRAME *frame;
29 {
30 	SYM *f;
31 	FRAME *frp;
32 	ADDRESS r, *dp, *disp;
33 	short offs;
34 
35 	f = s->func;
36 	if (s->class == FVAR) {
37 		offs = f->symvalue.offset;
38 	} else {
39 		offs = s->symvalue.offset;
40 	}
41 	if (f == program) {
42 		r = (ADDRESS) dispval(MAINBLK) + offs;
43 	} else if (f == curfunc && frame == NIL) {
44 		dp = curdp();
45 		disp = contents(dp);
46 		r = (ADDRESS) disp + offs;
47 	} else {
48 		if (frame == NIL) {
49 			frp = findframe(s->func);
50 			if (frp == NIL) {
51 				panic("address: findframe returned NIL");
52 			}
53 		} else {
54 			frp = frame;
55 		}
56 		r = stkaddr(frp, s->blkno) + offs;
57 	}
58 	return r;
59 }
60 
61 /*
62  * The next three routines assume the procedure entry code is
63  *
64  *		f:	tra4	A
65  *			...
66  *		A:	beg
67  *		B:	<code for first line>
68  *
69  * Pi gives f, we compute and store A with "findbeginning(f)",
70  * (retrieved by "codeloc(f)"), B is computed by "firstline(f)".
71  *
72  * The procedure "runtofirst" assumes you're at A and want to step to B.
73  * It should be changed to a nop if A is equal to B.
74  */
75 
76 /*
77  * Find the beginning of a procedure or function.  This is a destructive
78  * routine, it changes the value associated with the procedure symbol.
79  * Should only be called once per symbol.
80  */
81 
82 findbeginning(f)
83 SYM *f;
84 {
85 	f->symvalue.funcv.codeloc = nextaddr(f->symvalue.funcv.codeloc, FALSE);
86 }
87 
88 /*
89  * Find the object code associated with the first line of a block.
90  */
91 
92 ADDRESS firstline(f)
93 SYM *f;
94 {
95 	ADDRESS addr;
96 
97 	addr = codeloc(f);
98 	while (linelookup(addr) == 0) {
99 		addr = nextaddr(addr, FALSE);
100 	}
101 	return(addr);
102 }
103 
104 /*
105  * Catcher drops strike three ...
106  */
107 
108 runtofirst()
109 {
110 	stepto(firstline(curfunc));
111 }
112 
113 /*
114  * Calculate the address of the last line in the program.
115  * This is assumed to be at the physical end.
116  */
117 
118 ADDRESS lastaddr()
119 {
120 	if (objsize == 0) {
121 		panic("lastaddr: objsize = 0!");
122 	}
123 	return(objsize - sizeof(short));
124 }
125