checkin to only generate C for callable methods...
[IRC.git] / Robust / src / Runtime / object.c
1 #include "object.h"
2 #ifdef MULTICORE
3 #include "runtime_arch.h"
4 #else
5 #include "stdio.h"
6 #endif
7 #include "stdlib.h"
8
9 #ifdef THREADS
10 #include "thread.h"
11 #endif
12 #ifndef MULTICORE
13 #include "mlp_lock.h"
14 #endif
15
16 #ifdef D___Object______nativehashCode____
17 int CALL01(___Object______nativehashCode____, struct ___Object___ * ___this___) {
18   return (int)((INTPTR) VAR(___this___));
19 }
20 #endif
21
22 #ifdef D___Object______hashCode____
23 int CALL01(___Object______hashCode____, struct ___Object___ * ___this___) {
24   if (!VAR(___this___)->___cachedHash___) {
25     VAR(___this___)->___cachedHash___=1;
26     VAR(___this___)->___cachedCode___=(int)((INTPTR)VAR(___this___));
27   }
28   return VAR(___this___)->___cachedCode___;
29 }
30 #endif
31
32 #ifdef D___Object______getType____
33 int CALL01(___Object______getType____, struct ___Object___ * ___this___) {
34   return ((int *)VAR(___this___))[0];
35 }
36 #endif
37
38 #ifdef THREADS
39 #ifdef D___Object______MonitorEnter____
40 int CALL01(___Object______MonitorEnter____, struct ___Object___ * ___this___) {
41 #ifndef NOLOCK
42   pthread_t self=pthread_self();
43   if (self==VAR(___this___)->tid) {
44     atomic_inc(&VAR(___this___)->lockcount);
45   } else {
46     while(1) {
47       if (CAS32(&VAR(___this___)->lockcount, 0, 1)==0) {
48         VAR(___this___)->___prevlockobject___=NULL;
49         VAR(___this___)->___nextlockobject___=(struct ___Object___ *)pthread_getspecific(threadlocks);
50         if (VAR(___this___)->___nextlockobject___!=NULL)
51           VAR(___this___)->___nextlockobject___->___prevlockobject___=VAR(___this___);
52         pthread_setspecific(threadlocks, VAR(___this___));
53         VAR(___this___)->tid=self;
54         pthread_mutex_unlock(&objlock);
55         BARRIER();
56         return;
57       }
58       {
59 #ifdef PRECISE_GC
60         stopforgc((struct garbagelist *)___params___);
61 #endif
62 #ifdef PRECISE_GC
63         restartaftergc();
64 #endif
65       }
66     }
67   }
68 #endif
69 }
70 #endif
71
72
73 #ifdef D___Object______notify____
74 void CALL01(___Object______notify____, struct ___Object___ * ___this___) {
75 }
76 #endif
77
78 #ifdef D___Object______notifyAll____
79 void CALL01(___Object______notifyAll____, struct ___Object___ * ___this___) {
80 }
81 #endif
82
83 #ifdef D___Object______wait____
84 void CALL01(___Object______wait____, struct ___Object___ * ___this___) {
85   pthread_t self=pthread_self();
86   int lockcount=VAR(___this___)->lockcount;
87   //release lock
88   if (VAR(___this___)->___prevlockobject___==NULL) {
89     pthread_setspecific(threadlocks, VAR(___this___)->___nextlockobject___);
90   } else
91     VAR(___this___)->___prevlockobject___->___nextlockobject___=VAR(___this___)->___nextlockobject___;
92   if (VAR(___this___)->___nextlockobject___!=NULL)
93     VAR(___this___)->___nextlockobject___->___prevlockobject___=VAR(___this___)->___prevlockobject___;
94   VAR(___this___)->___nextlockobject___=NULL;
95   VAR(___this___)->___prevlockobject___=NULL;
96   //VAR(___this___)->lockentry=NULL;
97   VAR(___this___)->tid=0;
98   //release lock
99   BARRIER();
100   VAR(___this___)->lockcount=0;
101   
102   //allow gc
103 #ifdef PRECISE_GC
104   stopforgc((struct garbagelist *)___params___);
105 #endif
106   sched_yield();
107 #ifdef PRECISE_GC
108   restartaftergc();
109 #endif
110
111   while(1) {
112     if (CAS32(&VAR(___this___)->lockcount, 0, lockcount)==0) {
113       VAR(___this___)->___prevlockobject___=NULL;
114       VAR(___this___)->___nextlockobject___=(struct ___Object___ *)pthread_getspecific(threadlocks);
115       if (VAR(___this___)->___nextlockobject___!=NULL)
116         VAR(___this___)->___nextlockobject___->___prevlockobject___=VAR(___this___);
117       pthread_setspecific(threadlocks, VAR(___this___));
118       VAR(___this___)->tid=self;
119       pthread_mutex_unlock(&objlock);
120       BARRIER();
121       return;
122     }
123     {
124 #ifdef PRECISE_GC
125       stopforgc((struct garbagelist *)___params___);
126 #endif
127 #ifdef PRECISE_GC
128       restartaftergc();
129 #endif
130     }
131   }
132 }
133 #endif
134
135 #ifdef D___Object______MonitorExit____
136 int CALL01(___Object______MonitorExit____, struct ___Object___ * ___this___) {
137 #ifndef NOLOCK
138   pthread_t self=pthread_self();
139   if (self==VAR(___this___)->tid) {
140     //release one lock...
141     BARRIER();
142     if (VAR(___this___)->lockcount==1) {
143       if (VAR(___this___)->___prevlockobject___==NULL) {
144         pthread_setspecific(threadlocks, VAR(___this___)->___nextlockobject___);
145       } else
146         VAR(___this___)->___prevlockobject___->___nextlockobject___=VAR(___this___)->___nextlockobject___;
147       if (VAR(___this___)->___nextlockobject___!=NULL)
148         VAR(___this___)->___nextlockobject___->___prevlockobject___=VAR(___this___)->___prevlockobject___;
149       VAR(___this___)->___nextlockobject___=NULL;
150       VAR(___this___)->___prevlockobject___=NULL;
151       //VAR(___this___)->lockentry=NULL;
152       VAR(___this___)->tid=0;
153     }
154     atomic_dec(&VAR(___this___)->lockcount);
155   } else {
156 #ifdef MULTICORE
157     BAMBOO_EXIT(0xf201);
158 #else
159     printf("ERROR...UNLOCKING LOCK WE DON'T HAVE\n");
160     exit(-1);
161 #endif
162   }
163 #endif
164 }
165 #endif
166 #endif