History

My first initial commit with all of mine experimental changes.

Dmitry Kabak (userdima committed 13 years ago

Commit d37b88d1 parent 3f5b46618352 files · +2598093 −-8690Browse files

Showing the changes to java/tools/j2d/patch.c (1 of 18352 files). Show all

Unified · Split

java/tools/j2d/patch.c+132−0
@@ -0,0 +1,132 @@
1+#include "java.h"
2+
3+/*
4+ * Patch operands, etc. that reference pc offsets.
5+ */
6+
7+enum {
8+ P_CASE = 1,
9+ P_OTHER
10+};
11+
12+typedef struct Patch Patch;
13+
14+struct Patch {
15+ uchar kind; /* P_xxx */
16+ Inst *i;
17+ int n; /* number of cases in ... */
18+ int *jmptbl; /* ... case jump table */
19+ Patch *next;
20+};
21+
22+static Patch *plist;
23+
24+/*
25+ * Allocate a Patch structure.
26+ */
27+
28+static Patch*
29+newPatch(uchar kind, Inst *i)
30+{
31+ Patch *p;
32+
33+ p = Malloc(sizeof(Patch));
34+ p->kind = kind;
35+ p->i = i;
36+ p->next = plist;
37+ plist = p;
38+ return p;
39+}
40+
41+/*
42+ * Record non-case branch instruction for later patching.
43+ */
44+
45+void
46+patchop(Inst *i)
47+{
48+ newPatch(P_OTHER, i);
49+}
50+
51+/*
52+ * Record case jump table for later patching.
53+ */
54+
55+void
56+patchcase(Inst *i, int n, int *jmptbl)
57+{
58+ Patch *p;
59+
60+ p = newPatch(P_CASE, i);
61+ p->n = n;
62+ p->jmptbl = jmptbl;
63+}
64+
65+/*
66+ * Calculate patch address; Java branches are relative.
67+ */
68+
69+static int
70+patchaddr(Inst *i, int pc)
71+{
72+ Jinst *j;
73+ int span, srcjpc, dstjpc;
74+
75+ span = pc;
76+ srcjpc = i->j->pc;
77+ dstjpc = srcjpc + span;
78+ j = &code->j[dstjpc];
79+
80+ /* account for no-op's (dup, swap, pop, etc.), elided loads/stores */
81+ while(j->dis == nil)
82+ j += j->size;
83+
84+ return j->dis->pc;
85+}
86+
87+/*
88+ * Patch branch instructions and case jump tables of a method.
89+ */
90+
91+void
92+patchmethod(int startpc)
93+{
94+ Patch *p;
95+ Inst *i;
96+ int *jt;
97+ int n;
98+
99+ for(p = plist; p; p = p->next) {
100+ i = p->i;
101+ if(p->kind == P_CASE) {
102+ jt = p->jmptbl;
103+ for(n = 0; n < p->n; n++)
104+ jt[n*3+2] = patchaddr(i, jt[n*3+2]);
105+ jt[p->n*3] = patchaddr(i, jt[p->n*3]);
106+ } else { /* P_OTHER */
107+ i->d.u.ival = patchaddr(i, i->d.u.ival);
108+ /*
109+ * jmp $start_of_method -> jmp $start_of_method+1
110+ * skip (re-)allocation of Sys->Exception object
111+ */
112+ if(i->d.u.ival == startpc && i->op == IJMP && code->nex != 0)
113+ i->d.u.ival += 1;
114+ }
115+ }
116+}
117+
118+/*
119+ * Clear the patch list after each method.
120+ */
121+
122+void
123+patchfree(void)
124+{
125+ Patch *p, *p2;
126+
127+ for(p = plist; p; p = p2) {
128+ p2 = p->next;
129+ free(p);
130+ }
131+ plist = nil;
132+}

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t