Bug Summary

File:src/gf_java.c
Warning:line 740, column 38
Access to field 'id' results in a dereference of a null pointer

Annotated Source Code

Press '?' to see keyboard shortcuts

clang -cc1 -cc1 -triple x86_64-unknown-linux-gnu -analyze -disable-free -clear-ast-before-backend -disable-llvm-verifier -discard-value-names -main-file-name gf_java.c -analyzer-checker=core -analyzer-checker=apiModeling -analyzer-checker=unix -analyzer-checker=deadcode -analyzer-checker=security.insecureAPI.UncheckedReturn -analyzer-checker=security.insecureAPI.getpw -analyzer-checker=security.insecureAPI.gets -analyzer-checker=security.insecureAPI.mktemp -analyzer-checker=security.insecureAPI.mkstemp -analyzer-checker=security.insecureAPI.vfork -analyzer-checker=nullability.NullPassedToNonnull -analyzer-checker=nullability.NullReturnedFromNonnull -analyzer-output plist -w -setup-static-analyzer -mrelocation-model pic -pic-level 2 -pic-is-pie -mframe-pointer=all -fmath-errno -ffp-contract=on -fno-rounding-math -mconstructor-aliases -funwind-tables=2 -target-cpu x86-64 -tune-cpu generic -debugger-tuning=gdb -fdebug-compilation-dir=/home/kfp/aldor/aldor/aldor/src -fcoverage-compilation-dir=/home/kfp/aldor/aldor/aldor/src -resource-dir /usr/local/lib/clang/18 -D PACKAGE_NAME="aldor" -D PACKAGE_TARNAME="aldor" -D PACKAGE_VERSION="1.4.0" -D PACKAGE_STRING="aldor 1.4.0" -D PACKAGE_BUGREPORT="aldor@xinutec.org" -D PACKAGE_URL="" -D PACKAGE="aldor" -D VERSION="1.4.0" -D YYTEXT_POINTER=1 -D HAVE_STDIO_H=1 -D HAVE_STDLIB_H=1 -D HAVE_STRING_H=1 -D HAVE_INTTYPES_H=1 -D HAVE_STDINT_H=1 -D HAVE_STRINGS_H=1 -D HAVE_SYS_STAT_H=1 -D HAVE_SYS_TYPES_H=1 -D HAVE_UNISTD_H=1 -D STDC_HEADERS=1 -D HAVE_LIBREADLINE=1 -D HAVE_READLINE_READLINE_H=1 -D HAVE_READLINE_HISTORY=1 -D HAVE_READLINE_HISTORY_H=1 -D USE_GLOOP_SHELL=1 -D GENERATOR_COROUTINES=0 -D HAVE_DLFCN_H=1 -D LT_OBJDIR=".libs/" -I . -D VCSVERSION="2c53e759f1e00e345f8b172e7139debda72fda13" -internal-isystem /usr/local/lib/clang/18/include -internal-isystem /usr/local/include -internal-isystem /usr/lib/gcc/x86_64-linux-gnu/14/../../../../x86_64-linux-gnu/include -internal-externc-isystem /usr/include/x86_64-linux-gnu -internal-externc-isystem /include -internal-externc-isystem /usr/include -O0 -Wno-empty-body -Wno-enum-compare -Wno-missing-field-initializers -Wno-unused -Wno-unused-parameter -Wno-error=format -Wno-error=type-limits -Wno-error=strict-aliasing -Wno-sign-compare -Wno-error=shift-negative-value -Wno-error=clobbered -std=c99 -ferror-limit 19 -fgnuc-version=4.2.1 -fskip-odr-check-in-gmf -analyzer-output=html -faddrsig -D__GCC_HAVE_DWARF2_CFI_ASM=1 -o /tmp/scan-build-2026-01-15-223856-845667-1 -x c gf_java.c
1#include "axlobs.h"
2#include "debug.h"
3#include "format.h"
4#include "gf_util.h"
5#include "gf_prog.h"
6#include "gf_java.h"
7#include "gf_syme.h"
8#include "javasig.h"
9#include "optinfo.h"
10#include "table.h"
11#include "tinfer.h"
12#include "tform.h"
13#include "tqual.h"
14#include "stab.h"
15#include "strops.h"
16#include "symbol.h"
17#include "spesym.h"
18#include "util.h"
19
20localstatic AInt gfjFindConst(Syme syme);
21localstatic Foam gfjImportApply(Syme syme);
22localstatic AInt gfjImportApplyInner(Syme syme, AInt fmtNum);
23localstatic Foam gfjImportConstructor(Syme syme);
24localstatic Foam gfjImportStaticCall(Syme syme);
25localstatic FoamList gfjProgAddParams(TForm tf);
26
27localstatic TForm gfjPCallArgBaseJavaType(TForm tf);
28localstatic TForm gfjPCallRetBaseJavaType(TForm tf);
29localstatic FoamTag gfjPCallFoamType(TForm tf, AInt *pfmt);
30localstatic AInt gfjPCallFoamTypeDDecl(TForm tf);
31localstatic Foam gfjPCallFoamToJava(TForm tf, Foam foam);
32localstatic Foam gfjPCallJavaToFoam(TForm tf, Foam foam);
33localstatic AInt gfjPCallDeclImport(TForm tf, TForm this);
34localstatic AInt gfjPCallDeclExport(TForm tf, FoamProtoTag tag);
35localstatic Foam gfjPCallDeclArg(TForm tf);
36localstatic Foam gfjPCallDeclExn(TForm tf);
37localstatic Foam gfjPCallJavaToFoamForExport(TForm tf, Foam foam);
38localstatic Foam gfjPCallFoamToJavaForExport(TForm tf, Foam foam);
39
40localstatic AInt gj0ClassDDeclFull(String fullyQualifiedName);
41localstatic AInt gj0ClassDDecl(ForeignOrigin origin, String clsName);
42localstatic Foam gj0ClassDecl(ForeignOrigin origin, String clsName);
43
44localstatic String gfjDeclMethodNameForType(TForm tf, String methodName);
45localstatic String gfjDeclMethodName(String typeName, ForeignOrigin forg, String methodName);
46localstatic String gfjDeclClassNameForType(TForm tf);
47localstatic String gfjDeclClassName(String typeName, ForeignOrigin forg);
48
49localstatic AInt gfjExportDecoder(TForm tf);
50localstatic AInt gfjExportEncoder(TForm tf);
51
52static Table gfjExportEncoderForTForm;
53static Table gfjExportDecoderForTForm;
54
55void
56gfjInit()
57{
58 gfjExportEncoderForTForm = tblNew((TblHashFun) tfHash, (TblEqFun) tfEqual);
59 gfjExportDecoderForTForm = tblNew((TblHashFun) tfHash, (TblEqFun) tfEqual);
60}
61
62void
63gfjFini()
64{
65 tblFree(gfjExportEncoderForTForm);
66 tblFree(gfjExportDecoderForTForm);
67 gfjExportEncoderForTForm = NULL((void*)0);
68 gfjExportDecoderForTForm = NULL((void*)0);
69}
70
71
72Foam
73gfjGetImport(Syme syme)
74{
75 if (symeIsJavaApply(syme))
76 return gfjImportApply(syme);
77 else if (symeIsJavaConstructor(syme))
78 return gfjImportConstructor(syme);
79 else
80 return gfjImportStaticCall(syme);
81}
82
83void
84gfjVarImport(Syme syme, Stab stab)
85{
86}
87
88localstatic Foam
89gfjImportApply(Syme syme)
90{
91 GenFoamState saved;
92 Foam prog;
93 String fnName;
94 AInt fmtNum, innerConstNum, constNum;
95 fnName = strCopy(symeJavaApplyName(syme));
96
97 constNum = gen0NumProgs;
98
99 prog = gen0ProgInitEmpty(fnName, NULL((void*)0));
100 saved = gen0ProgSaveState(PT_ExFn);
101
102 fmtNum = gen0FormatNum--;
103
104 innerConstNum = gfjImportApplyInner(syme, fmtNum);
105
106 gen0AddParam(foamNewDecl(FOAM_Word, strCopy("this"), emptyFormatSlot)foamNew(FOAM_Decl,4,(AInt)(FOAM_Word),strCopy("this"), (AInt)
(0x7FFF), 4)
);
107
108 gen0AddStmt(foamNewDef(foamNewLex(int0, int0), foamNewPar(int0))foamNew(FOAM_Def, 2, foamNew(FOAM_Lex, 2, (AInt)(((int) 0)), (
AInt)(((int) 0))), foamNew(FOAM_Par, 1, (AInt)(((int) 0))))
, NULL((void*)0));
109 gen0AddStmt(foamNewReturn(foamNewCast(FOAM_Word,foamNew(FOAM_Return, 1, foamNew(FOAM_Cast, 2, FOAM_Word, foamNew
(FOAM_Clos,2, foamNew(FOAM_Env, 1, (AInt)(((int) 0))), foamNew
(FOAM_Const, 1, (AInt)(innerConstNum)))))
110 foamNewClos(foamNewEnv(int0), foamNewConst(innerConstNum))))foamNew(FOAM_Return, 1, foamNew(FOAM_Cast, 2, FOAM_Word, foamNew
(FOAM_Clos,2, foamNew(FOAM_Env, 1, (AInt)(((int) 0))), foamNew
(FOAM_Const, 1, (AInt)(innerConstNum)))))
, NULL((void*)0));
111
112 gen0ProgAddFormat(fmtNum,
113 foamNewDDecl(FOAM_DDecl_LocalEnv,
114 foamNewDecl(FOAM_Word, strCopy("this"), emptyFormatSlot)foamNew(FOAM_Decl,4,(AInt)(FOAM_Word),strCopy("this"), (AInt)
(0x7FFF), 4)
,
115 NULL((void*)0)));
116
117 gen0ProgFiniEmpty(prog, FOAM_Word, emptyFormatSlot4);
118 foamOptInfo(prog)((prog)->hdr.info.opt) = optInfoNew(NULL((void*)0), prog, NULL((void*)0), false((int) 0));
119 gen0ProgRestoreState(saved);
120 genSetConstNum(syme, -1, constNum, true1);
121 return foamNewClos(foamNewEnv(int0), foamNewConst(constNum))foamNew(FOAM_Clos,2, foamNew(FOAM_Env, 1, (AInt)(((int) 0))),
foamNew(FOAM_Const, 1, (AInt)(constNum)))
;
122}
123
124localstatic AInt
125gfjImportApplyInner(Syme syme, AInt fmtNum)
126{
127 GenFoamState saved;
128 TForm exporter, innerTf;
129 FoamList params;
130 Foam gdecl, prog, pcall, temp, op;
131 FoamTag retType;
132 String fnName, globName;
133 AInt gnum, constnum;
134 AInt clsFmt;
135
136 constnum = gen0NumProgs;
137
138 exporter = symeExporter(syme);
139 innerTf = tfMapRet(symeType(syme))tfFollowArg(symeType(syme), 1);
140
141 clsFmt = gfjPCallFoamTypeDDecl(exporter);
142
143 globName = gfjDeclMethodNameForType(exporter, symeJavaApplyName(syme));
144
145 gdecl = foamNewGDecl(FOAM_Clos, globName, FOAM_Nil,foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,gfjPCallDeclImport
(innerTf, tfMapArgN(symeType(syme), 0)), (AInt)(FOAM_GDecl_Import
),(AInt)(FOAM_Proto_JavaMethod))
146 gfjPCallDeclImport(innerTf, tfMapArgN(symeType(syme), 0)),foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,gfjPCallDeclImport
(innerTf, tfMapArgN(symeType(syme), 0)), (AInt)(FOAM_GDecl_Import
),(AInt)(FOAM_Proto_JavaMethod))
147 FOAM_GDecl_Import, FOAM_Proto_JavaMethod)foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,gfjPCallDeclImport
(innerTf, tfMapArgN(symeType(syme), 0)), (AInt)(FOAM_GDecl_Import
),(AInt)(FOAM_Proto_JavaMethod))
;
148 gnum = gen0AddGlobal(gdecl);
149 fnName = strPrintf("%s-inner", symeJavaApplyName(syme));
150
151 prog = gen0ProgInitEmpty(fnName, NULL((void*)0));
152 saved = gen0ProgSaveState(PT_ExFn);
153
154 temp = gen0TempLocal0(FOAM_JavaObj, clsFmt);
155 gen0AddStmt(foamNewDef(foamCopy(temp), foamNewCast(FOAM_JavaObj, foamNewLex(1, int0)))foamNew(FOAM_Def, 2, foamCopy(temp), foamNew(FOAM_Cast, 2, FOAM_JavaObj
, foamNew(FOAM_Lex, 2, (AInt)(1), (AInt)(((int) 0)))))
, NULL((void*)0));
156
157 params = gfjProgAddParams(innerTf);
158 params = listCons(Foam)(Foam_listPointer->Cons)(foamCopy(temp), params);
159 op = foamNewGlo(gnum)foamNew(FOAM_Glo, 1, (AInt)(gnum));
160
161 retType = tfMapRetc(innerTf) == 0 ? FOAM_NOp: FOAM_Word;
162 if (retType == FOAM_NOp) {
163 pcall = foamNewPCallOfList(FOAM_Proto_JavaMethod,
164 FOAM_NOp, op, params);
165 gen0AddLexLevels(pcall, 2);
166 gen0AddStmt(pcall, NULL((void*)0));
167 }
168 else {
169 FoamTag type = gfjPCallFoamType(tfMapRet(innerTf)tfFollowArg(innerTf, 1), NULL((void*)0));
170 Foam pcall = foamNewPCallOfList(FOAM_Proto_JavaMethod,
171 type, op, params);
172 Foam retval = gfjPCallJavaToFoam(tfMapRet(innerTf)tfFollowArg(innerTf, 1), pcall);
173 gen0AddLexLevels(retval, 2);
174 gen0AddStmt(foamNewReturn(retval)foamNew(FOAM_Return, 1, retval), NULL((void*)0));
175 }
176 foamFree(temp);
177 gen0ProgPushFormat(fmtNum);
178 gen0ProgPushFormat(emptyFormatSlot4);
179
180 gen0ProgFiniEmpty(prog, retType, emptyFormatSlot4);
181 foamOptInfo(prog)((prog)->hdr.info.opt) = optInfoNew(NULL((void*)0), prog, NULL((void*)0), false((int) 0));
182
183 gen0ProgRestoreState(saved);
184 return constnum;
185}
186
187localstatic Foam
188gfjImportConstructor(Syme syme)
189{
190 GenFoamState saved;
191 TForm exporter;
192 FoamList params;
193 Foam prog, gdecl, pcall;
194 String fnName, globName;
195 AInt fmtNum, innerConstNum, constNum, gnum;
196
197 exporter = symeExporter(syme);
198 globName = gfjDeclClassNameForType(exporter);
199 fnName = strCopy(globName);
200
201 constNum = gen0NumProgs;
202
203 gdecl = foamNewGDecl(FOAM_Clos, globName, FOAM_Nil,foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,gfjPCallDeclImport
(symeType(syme), ((void*)0)), (AInt)(FOAM_GDecl_Import),(AInt
)(FOAM_Proto_JavaConstructor))
204 gfjPCallDeclImport(symeType(syme), NULL),foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,gfjPCallDeclImport
(symeType(syme), ((void*)0)), (AInt)(FOAM_GDecl_Import),(AInt
)(FOAM_Proto_JavaConstructor))
205 FOAM_GDecl_Import, FOAM_Proto_JavaConstructor)foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,gfjPCallDeclImport
(symeType(syme), ((void*)0)), (AInt)(FOAM_GDecl_Import),(AInt
)(FOAM_Proto_JavaConstructor))
;
206 gnum = gen0AddGlobal(gdecl);
207
208 prog = gen0ProgInitEmpty(fnName, NULL((void*)0));
209 saved = gen0ProgSaveState(PT_ExFn);
210
211 params = gfjProgAddParams(symeType(syme));
212
213 pcall = foamNewPCallOfList(FOAM_Proto_JavaConstructor,
214 gfjPCallFoamType(exporter, NULL((void*)0)),
215 foamNewGlo(gnum)foamNew(FOAM_Glo, 1, (AInt)(gnum)), params);
216
217 gen0AddLexLevels(pcall, 1);
218 gen0ProgPushFormat(emptyFormatSlot4);
219
220 gen0AddStmt(foamNewReturn(foamNewCast(FOAM_Word, pcall))foamNew(FOAM_Return, 1, foamNew(FOAM_Cast, 2, FOAM_Word, pcall
))
, NULL((void*)0));
221
222 gen0ProgFiniEmpty(prog, FOAM_Word, emptyFormatSlot4);
223 foamOptInfo(prog)((prog)->hdr.info.opt) = optInfoNew(NULL((void*)0), prog, NULL((void*)0), false((int) 0));
224 gen0ProgRestoreState(saved);
225
226 genSetConstNum(syme, -1, constNum, true1);
227 return foamNewClos(foamNewEnv(int0), foamNewConst(constNum))foamNew(FOAM_Clos,2, foamNew(FOAM_Env, 1, (AInt)(((int) 0))),
foamNew(FOAM_Const, 1, (AInt)(constNum)))
;
228}
229
230localstatic Foam
231gfjImportStaticCall(Syme syme)
232{
233 GenFoamState saved;
234 ForeignOrigin forg;
235 TForm exporter;
236 Syme esyme;
237 FoamList params;
238 Foam prog, gdecl, pcall;
239 FoamTag retType;
240 String fnName, globName;
241 AInt fmtNum, innerConstNum, constNum, gnum;
242
243 exporter = symeExporter(syme);
244 fnName = strCopy(symeString(syme)((((syme)->id))->str));
245
246 globName = gfjDeclMethodNameForType(exporter, symeString(syme)((((syme)->id))->str));
247
248 constNum = gen0NumProgs;
249
250 gdecl = foamNewGDecl(FOAM_Clos, globName,foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,gfjPCallDeclImport
(symeType(syme), ((void*)0)), (AInt)(FOAM_GDecl_Import),(AInt
)(FOAM_Proto_Java))
251 FOAM_Nil,foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,gfjPCallDeclImport
(symeType(syme), ((void*)0)), (AInt)(FOAM_GDecl_Import),(AInt
)(FOAM_Proto_Java))
252 gfjPCallDeclImport(symeType(syme), NULL),foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,gfjPCallDeclImport
(symeType(syme), ((void*)0)), (AInt)(FOAM_GDecl_Import),(AInt
)(FOAM_Proto_Java))
253 FOAM_GDecl_Import, FOAM_Proto_Java)foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,gfjPCallDeclImport
(symeType(syme), ((void*)0)), (AInt)(FOAM_GDecl_Import),(AInt
)(FOAM_Proto_Java))
;
254 gnum = gen0AddGlobal(gdecl);
255
256 prog = gen0ProgInitEmpty(fnName, NULL((void*)0));
257 saved = gen0ProgSaveState(PT_ExFn);
258
259 params = gfjProgAddParams(symeType(syme));
260 retType = gfjPCallFoamType(tfMapRet(symeType(syme))tfFollowArg(symeType(syme), 1), NULL((void*)0));
261 pcall = foamNewPCallOfList(FOAM_Proto_Java,
262 retType,
263 foamNewGlo(gnum)foamNew(FOAM_Glo, 1, (AInt)(gnum)), params);
264
265 gen0AddLexLevels(pcall, 1);
266 gen0ProgPushFormat(emptyFormatSlot4);
267 gen0AddStmt(foamNewReturn(foamNewCast(FOAM_Word, pcall))foamNew(FOAM_Return, 1, foamNew(FOAM_Cast, 2, FOAM_Word, pcall
))
, NULL((void*)0));
268
269 gen0ProgFiniEmpty(prog, FOAM_Word, emptyFormatSlot4);
270 foamOptInfo(prog)((prog)->hdr.info.opt) = optInfoNew(NULL((void*)0), prog, NULL((void*)0), false((int) 0));
271 gen0ProgRestoreState(saved);
272
273 genSetConstNum(syme, -1, constNum, true1);
274 return foamNewClos(foamNewEnv(int0), foamNewConst(constNum))foamNew(FOAM_Clos,2, foamNew(FOAM_Env, 1, (AInt)(((int) 0))),
foamNew(FOAM_Const, 1, (AInt)(constNum)))
;
275}
276
277localstatic FoamList
278gfjProgAddParams(TForm tf)
279{
280 FoamList params = listNil(Foam)((FoamList) 0);
281 int i;
282
283 for (i=0; i<tfMapArgc(tf); i++) {
284 AInt idx = gen0AddParam(foamNewDecl(FOAM_Word, strPrintf("%d", i),foamNew(FOAM_Decl,4,(AInt)(FOAM_Word),strPrintf("%d", i), (AInt
) (0x7FFF), 4)
285 emptyFormatSlot)foamNew(FOAM_Decl,4,(AInt)(FOAM_Word),strPrintf("%d", i), (AInt
) (0x7FFF), 4)
);
286 Foam converted = gfjPCallFoamToJava(tfMapArgN(tf, i), foamNewPar(idx)foamNew(FOAM_Par, 1, (AInt)(idx)));
287 params = listCons(Foam)(Foam_listPointer->Cons)(converted, params);
288 }
289 return listNReverse(Foam)(Foam_listPointer->NReverse)(params);
290}
291
292/*
293 * :: Java representation
294 *
295 * Aldor types used in Java imports are assumed to have toJava and fromJava methods
296 * which convert to and from java respectively.
297 */
298localstatic FoamTag
299gfjPCallFoamType(TForm tf, AInt *pfmt)
300{
301 tf = tfIgnoreExceptions(tf);
302 if (tfIsJavaImport(tf)) {
303 if (pfmt != NULL((void*)0)) {
304 *pfmt = gfjPCallFoamTypeDDecl(tf);
305 }
306 return FOAM_JavaObj;
307 }
308 else if (stabIsForeignExport(gen0State->stab, tf)) {
309 if (pfmt != NULL((void*)0)) {
310 ForeignOrigin forg = stabForeignExportLocation(gen0State->stab, tf);
311 *pfmt = gj0ClassDDecl(forg, symeString(tfIdSyme(tf))((((((((tf)->__absyn))->abHdr.seman ? (((tf)->__absyn
))->abHdr.seman->syme : 0))->id))->str)
);
312 }
313 return FOAM_JavaObj;
314 }
315 else {
316 Syme javaToSelf = tfGetDomImport(tf, symString(ssymTheFromJava)((ssymTheFromJava)->str),
317 tfIsJavaDecoder);
318 if (javaToSelf != NULL((void*)0)) {
319 TForm convTf = symeType(javaToSelf);
320 tfFollow(convTf)((convTf) = tfFollowFn(convTf));
321 return gfjPCallFoamType(tfMapArg(convTf)tfFollowArg(convTf, 0), pfmt);
322 }
323 else {
324 return gen0Type(tf, pfmt);
325 }
326 }
327}
328
329
330localstatic Foam
331gfjPCallFoamToJava(TForm tf, Foam foam)
332{
333 tf = tfIgnoreExceptions(tf);
334
335 if (tfIsJavaImport(tf)) {
336 return foamNewCast(FOAM_JavaObj, foam)foamNew(FOAM_Cast, 2, FOAM_JavaObj, foam);
337 }
338 else if (stabIsForeignExport(gen0State->stab, tf)) {
339 return gfjPCallFoamToJavaForExport(tf, foam);
340 }
341 else {
342 if (tfIsId(tf)((((tf)->tag) == TF_General) && ((((tf)->__absyn
))->abHdr.tag) == AB_Id)
&& symeExtension(tfIdSyme(tf)((((tf)->__absyn))->abHdr.seman ? (((tf)->__absyn))->
abHdr.seman->syme : 0)
)) {
343 Syme syme = tfIdSyme(tf)((((tf)->__absyn))->abHdr.seman ? (((tf)->__absyn))->
abHdr.seman->syme : 0)
;
344 syme = symeExtensionFull(syme);
345 tf = tfFrSyme(stabFile(), syme);
346 }
347
348 Syme selfToJava = tfGetDomImport(tf,
349 symString(ssymTheToJava)((ssymTheToJava)->str),
350 tfIsJavaEncoder);
351 if (selfToJava != NULL((void*)0)) {
352 TForm convTf = symeType(selfToJava);
353 tfFollow(convTf)((convTf) = tfFollowFn(convTf));
354 TForm retTf = tfMapRetN(convTf, 0);
355 FoamTag type = gen0Type(retTf, NULL((void*)0));
356 Foam call;
357 call = gen0ExtendSyme(selfToJava);
358 call = foamNewCCall(type, call, foam, NULL((void*)0));
359 return gfjPCallFoamToJava(retTf, call);
360 }
361 else {
362 return foam;
363 }
364 }
365}
366
367localstatic Foam
368gfjPCallJavaToFoam(TForm tf, Foam foam)
369{
370 tf = tfIgnoreExceptions(tf);
371
372 if (tfIsJavaImport(tf)) {
373 return foamNewCast(FOAM_Word, foam)foamNew(FOAM_Cast, 2, FOAM_Word, foam);
374 }
375 else if (stabIsForeignExport(gen0State->stab, tf)) {
376 return gfjPCallJavaToFoamForExport(tf, foam);
377 }
378 else {
379 if (tfIsId(tf)((((tf)->tag) == TF_General) && ((((tf)->__absyn
))->abHdr.tag) == AB_Id)
&& symeExtension(tfIdSyme(tf)((((tf)->__absyn))->abHdr.seman ? (((tf)->__absyn))->
abHdr.seman->syme : 0)
)) {
380 Syme syme = tfIdSyme(tf)((((tf)->__absyn))->abHdr.seman ? (((tf)->__absyn))->
abHdr.seman->syme : 0)
;
381 syme = symeExtensionFull(syme);
382 tf = tfFrSyme(stabFile(), syme);
383 }
384
385 Syme javaToSelf = tfGetDomImport(tf,
386 symString(ssymTheFromJava)((ssymTheFromJava)->str),
387 tfIsJavaDecoder);
388 Foam call;
389 call = gen0ExtendSyme(javaToSelf);
390 call = foamNewCCall(FOAM_Word, call, foam, NULL((void*)0));
391
392 return call;
393 }
394}
395
396localstatic Foam
397gfjPCallJavaToFoamForExport(TForm tf, Foam foam)
398{
399 AInt gnum = gfjExportDecoder(tf);
400 return foamNewPCallOfList(FOAM_Proto_JavaMethod, FOAM_Word,
401 foamNewGlo(gnum)foamNew(FOAM_Glo, 1, (AInt)(gnum)),
402 listSingleton(Foam)(Foam_listPointer->Singleton)(foam));
403}
404
405localstatic Foam
406gfjPCallFoamToJavaForExport(TForm tf, Foam foam)
407{
408 AInt gnum = gfjExportEncoder(tf);
409 return foamNewPCallOfList(FOAM_Proto_JavaConstructor, FOAM_JavaObj,
410 foamNewGlo(gnum)foamNew(FOAM_Glo, 1, (AInt)(gnum)),
411 listSingleton(Foam)(Foam_listPointer->Singleton)(foam));
412}
413
414
415localstatic AInt
416gfjPCallDeclImport(TForm tf, TForm this)
417{
418 TForm retTf;
419 FoamList decls;
420 Foam ddecl, retdecl, exndecl;
421 int i;
422
423 decls = listNil(Foam)((FoamList) 0);
424
425 if (this != NULL((void*)0)) {
426 TForm tfThis = gfjPCallArgBaseJavaType(this);
427 Foam decl = gfjPCallDeclArg(tfThis);
428 decls = listCons(Foam)(Foam_listPointer->Cons)(decl, decls);
429 }
430
431 for (i=0; i<tfMapArgc(tf); i++) {
432 TForm tfi = gfjPCallArgBaseJavaType(tfMapArgN(tf, i));
433 Foam decl = gfjPCallDeclArg(tfi);
434 decls = listCons(Foam)(Foam_listPointer->Cons)(decl, decls);
435 }
436
437 retTf = tfMapRet(tf)tfFollowArg(tf, 1);
438 retdecl = gfjPCallDeclArg(gfjPCallRetBaseJavaType(retTf));
439 exndecl = gfjPCallDeclExn(tfIsExcept(retTf)(((retTf)->tag) == TF_Except) ? tfExceptExcept(retTf)tfFollowArg(retTf, 1): NULL((void*)0));
440
441 ddecl = javaSigNew(retdecl, exndecl, listNReverse(Foam)(Foam_listPointer->NReverse)(decls));
442
443 return gen0AddRealFormat(ddecl);
444
445}
446
447localstatic AInt
448gfjPCallDeclExport(TForm tf, FoamProtoTag protocol)
449{
450 FoamList decls;
451 Foam ddecl, retdecl, exndecl;
452 int i;
453
454 decls = listNil(Foam)((FoamList) 0);
455
456 for (i=0; i<tfMapArgc(tf); i++) {
457 TForm tfi = gfjPCallArgBaseJavaType(tfMapArgN(tf, i));
458 Foam decl = gfjPCallDeclArg(tfi);
459 decls = listCons(Foam)(Foam_listPointer->Cons)(decl, decls);
460 }
461
462 retdecl = protocol == FOAM_Proto_JavaConstructor
463 ? foamNewDecl(FOAM_Word, strCopy(""), emptyFormatSlot)foamNew(FOAM_Decl,4,(AInt)(FOAM_Word),strCopy(""), (AInt) (0x7FFF
), 4)
464 : gfjPCallDeclArg(gfjPCallRetBaseJavaType(tfMapRet(tf)tfFollowArg(tf, 1)));
465
466 exndecl = gfjPCallDeclExn(tfIsExcept(tfMapRet(tf))(((tfFollowArg(tf, 1))->tag) == TF_Except) ? tfExceptExcept(tfMapRet(tf))tfFollowArg(tfFollowArg(tf, 1), 1): NULL((void*)0));
467
468 ddecl = javaSigNew(retdecl, exndecl, listNReverse(Foam)(Foam_listPointer->NReverse)(decls));
469
470 return gen0AddRealFormat(ddecl);
471}
472
473localstatic TForm
474gfjPCallArgBaseJavaType(TForm tf)
475{
476 int i = 0;
477 while (i<5) {
478 Syme enc = tfGetDomExport(tf, symString(ssymTheFromJava)((ssymTheFromJava)->str), tfIsJavaDecoder);
479 if (enc == NULL((void*)0)) {
480 return tf;
481 }
482 TForm retType = tfMapArg(symeType(enc))tfFollowArg(symeType(enc), 0);
483 tf = retType;
484 i++;
485 }
486
487 bug("Recursive fromJava?");
488 return NULL((void*)0);
489}
490
491localstatic TForm
492gfjPCallRetBaseJavaType(TForm tf)
493{
494 int i = 0;
495 tf = tfIgnoreExceptions(tf);
496
497 while (i<5) {
498 Syme enc = tfGetDomExport(tf, symString(ssymTheToJava)((ssymTheToJava)->str), tfIsJavaEncoder);
499 if (enc == NULL((void*)0)) {
500 return tf;
501 }
502 TForm retType = tfMapRet(symeType(enc))tfFollowArg(symeType(enc), 1);
503 tf = retType;
504 i++;
505 }
506
507 bug("Recursive toJava?");
508 return NULL((void*)0);
509}
510
511localstatic Foam
512gfjPCallDeclArg(TForm tf)
513{
514 String id = "";
515 Foam decl;
516
517 if (tfIsDeclare(tf)(((tf)->tag) == TF_Declare)) {
518 id = symString(tfDeclareId(tf))((tfDeclareId(tf))->str);
519 tf = tfDeclareType(tf)tfFollowArg(tf, 0);
520 }
521
522 if (tfIsJavaImport(tf)) {
523 AInt fmt = gfjPCallFoamTypeDDecl(tf);
524 decl = foamNewDecl(FOAM_JavaObj, strCopy(id), fmt)foamNew(FOAM_Decl,4,(AInt)(FOAM_JavaObj),strCopy(id), (AInt) (
0x7FFF), fmt)
;
525 }
526 else if (stabIsForeignExport(gen0State->stab, tf)) {
527 assert(tfIsId(tf))do { if (!(((((tf)->tag) == TF_General) && ((((tf)
->__absyn))->abHdr.tag) == AB_Id))) _do_assert(("tfIsId(tf)"
),"gf_java.c",527); } while (0)
;
528 ForeignOrigin forg = stabForeignExportLocation(gen0State->stab, tf);
529 Syme syme = abSyme(tfExpr(tf))((tfToAbSyn(tf))->abHdr.seman ? (tfToAbSyn(tf))->abHdr.
seman->syme : 0)
;
530 AInt fmt = gj0ClassDDecl(forg, symeString(syme)((((syme)->id))->str));
531 decl = foamNewDecl(FOAM_JavaObj, strCopy(id), fmt)foamNew(FOAM_Decl,4,(AInt)(FOAM_JavaObj),strCopy(id), (AInt) (
0x7FFF), fmt)
;
532 }
533 else {
534 FoamTag type;
535 AInt fmt;
536 type = gen0Type(tf, &fmt);
537 decl = foamNewDecl(type, strCopy(id), fmt)foamNew(FOAM_Decl,4,(AInt)(type),strCopy(id), (AInt) (0x7FFF)
, fmt)
;
538 }
539
540 return decl;
541}
542
543localstatic Foam
544gfjPCallDeclExn(TForm tf)
545{
546 Foam decl;
547
548 if (tf == NULL((void*)0)) {
549 decl = foamNewDecl(FOAM_NOp, strCopy(""), emptyFormatSlot)foamNew(FOAM_Decl,4,(AInt)(FOAM_NOp),strCopy(""), (AInt) (0x7FFF
), 4)
;
550 }
551 else {
552 // For the moment, everything maps to exception.
553 decl = foamNewDecl(FOAM_JavaObj, strCopy("exn"),foamNew(FOAM_Decl,4,(AInt)(FOAM_JavaObj),strCopy("exn"), (AInt
) (0x7FFF), gj0ClassDDeclFull(strCopy("java.lang.Exception"))
)
554 gj0ClassDDeclFull(strCopy("java.lang.Exception")))foamNew(FOAM_Decl,4,(AInt)(FOAM_JavaObj),strCopy("exn"), (AInt
) (0x7FFF), gj0ClassDDeclFull(strCopy("java.lang.Exception"))
)
;
555 }
556 return decl;
557}
558
559localstatic AInt gfjPCallFoamTypeDDeclAbSyn(AbSyn);
560localstatic AInt gfjPCallFoamTypeDDeclId (AbSyn);
561
562localstatic AInt
563gfjPCallFoamTypeDDecl(TForm tf)
564{
565 return gfjPCallFoamTypeDDeclAbSyn(tfExpr(tf)tfToAbSyn(tf));
566}
567
568localstatic AInt
569gfjPCallFoamTypeDDeclAbSyn(AbSyn ab)
570{
571 AInt fmt;
572 if (abIsId(ab)((ab)->abHdr.tag == (AB_Id))) {
573 return gfjPCallFoamTypeDDeclId(ab);
574 }
575 else if (abIsApply(ab)((ab)->abHdr.tag == (AB_Apply))) {
576 Syme opSyme = abSyme(ab->abApply.op)((ab->abApply.op)->abHdr.seman ? (ab->abApply.op)->
abHdr.seman->syme : 0)
;
577 ForeignOrigin forg = symeForeign(opSyme)((ForeignOrigin) (SYFI_Foreign < (8 * sizeof(int)) &&
!(((((opSyme)->kind == SYME_Trigger ? libGetAllSymes((opSyme
)->lib) : ((void*)0)), (opSyme))->hasmask) & (1 <<
(SYFI_Foreign))) ? (symeFieldInfo[SYFI_Foreign].def) : (((((
opSyme)->kind == SYME_Trigger ? libGetAllSymes((opSyme)->
lib) : ((void*)0)), (opSyme))->locmask) & (1 << (
SYFI_Foreign))) ? ((((((opSyme)->kind == SYME_Trigger ? libGetAllSymes
((opSyme)->lib) : ((void*)0)), (opSyme))->locmask) &
(1 << (SYFI_Foreign))) ? ((opSyme)->fieldv)[symeIndex
(opSyme,SYFI_Foreign)] : (symeFieldInfo[SYFI_Foreign].def)) :
symeGetFieldFn(opSyme,SYFI_Foreign)))
;
578 String name = gfjDeclClassName(symeString(opSyme)((((opSyme)->id))->str), forg);
579 Foam opDecl = foamNewDecl(FOAM_JavaObj, name, int0)foamNew(FOAM_Decl,4,(AInt)(FOAM_JavaObj),name, (AInt) (0x7FFF
), ((int) 0))
;
580 FoamList args = listNil(Foam)((FoamList) 0);
581 int i;
582 for (i=0; i<abApplyArgc(ab)(((ab)->abHdr.argc)-1); i++) {
583 TForm argTf = abTForm(abApplyArg(ab, i))((((ab)->abApply.argv[i]))->abHdr.seman ? (((ab)->abApply
.argv[i]))->abHdr.seman->tform : 0)
584 ? abTForm(abApplyArg(ab, i))((((ab)->abApply.argv[i]))->abHdr.seman ? (((ab)->abApply
.argv[i]))->abHdr.seman->tform : 0)
585 : tiGetTForm(gen0State->stab, abApplyArg(ab, i)((ab)->abApply.argv[i]));
586 AInt fmt;
587 FoamTag tag = gfjPCallFoamType(argTf, &fmt);
588 Foam decl = foamNewDecl(tag, aStrPrintf("%d", i), fmt)foamNew(FOAM_Decl,4,(AInt)(tag),aStrPrintf("%d", i), (AInt) (
0x7FFF), fmt)
;
589 args = listCons(Foam)(Foam_listPointer->Cons)(decl, args);
590 }
591 args = listNReverse(Foam)(Foam_listPointer->NReverse)(args);
592 return gen0AddRealFormat(foamNewDDeclOfList(FOAM_DDecl_JavaClass,
593 listCons(Foam)(Foam_listPointer->Cons)(opDecl, args)));
594 }
595 else {
596 afprintf(dbOut, "%pAbSyn\n", ab);
597 bug("Unknown conversion");
598 }
599}
600
601localstatic AInt
602gfjPCallFoamTypeDDeclId(AbSyn id)
603{
604 TForm tf = abTForm(id)((id)->abHdr.seman ? (id)->abHdr.seman->tform : 0) ? abTForm(id)((id)->abHdr.seman ? (id)->abHdr.seman->tform : 0): tiGetTForm(gen0State->stab, id);
605 Syme syme = tfIdSyme(tf)((((tf)->__absyn))->abHdr.seman ? (((tf)->__absyn))->
abHdr.seman->syme : 0)
;
606 ForeignOrigin forg = symeForeign(syme)((ForeignOrigin) (SYFI_Foreign < (8 * sizeof(int)) &&
!(((((syme)->kind == SYME_Trigger ? libGetAllSymes((syme)
->lib) : ((void*)0)), (syme))->hasmask) & (1 <<
(SYFI_Foreign))) ? (symeFieldInfo[SYFI_Foreign].def) : (((((
syme)->kind == SYME_Trigger ? libGetAllSymes((syme)->lib
) : ((void*)0)), (syme))->locmask) & (1 << (SYFI_Foreign
))) ? ((((((syme)->kind == SYME_Trigger ? libGetAllSymes((
syme)->lib) : ((void*)0)), (syme))->locmask) & (1 <<
(SYFI_Foreign))) ? ((syme)->fieldv)[symeIndex(syme,SYFI_Foreign
)] : (symeFieldInfo[SYFI_Foreign].def)) : symeGetFieldFn(syme
,SYFI_Foreign)))
;
607 String name = gfjDeclClassName(symeString(syme)((((syme)->id))->str), forg);
608 AInt fmt = gj0ClassDDecl(forg, symeString(syme)((((syme)->id))->str));
609
610 return fmt;
611}
612
613
614localstatic AInt
615gj0ClassDDecl(ForeignOrigin origin, String clsName)
616{
617 String name = gfjDeclClassName(clsName, origin);
618 return gj0ClassDDeclFull(name);
619}
620
621localstatic AInt
622gj0ClassDDeclFull(String fullyQualifiedName)
623{
624 Foam decl = foamNewDecl(FOAM_JavaObj, fullyQualifiedName, int0)foamNew(FOAM_Decl,4,(AInt)(FOAM_JavaObj),fullyQualifiedName, (
AInt) (0x7FFF), ((int) 0))
;
625
626 return gen0AddRealFormat(foamNewDDecl(FOAM_DDecl_JavaClass, decl, NULL((void*)0)));
627}
628
629localstatic Foam
630gj0ClassDecl(ForeignOrigin origin, String clsName)
631{
632 return foamNewDecl(FOAM_JavaObj, strCopy(clsName), gj0ClassDDecl(origin, clsName))foamNew(FOAM_Decl,4,(AInt)(FOAM_JavaObj),strCopy(clsName), (AInt
) (0x7FFF), gj0ClassDDecl(origin, clsName))
;
633}
634
635/*
636 * :: Export to java
637 */
638
639localstatic void gfjExportToJavaClass(AbSyn syme, ForeignOrigin forg);
640localstatic void gfjExportToJavaSyme(TForm tf, Syme syme, Foam clos);
641localstatic String gfjExportToJavaSymeMethodName(Syme syme);
642localstatic AInt gfjExportToJavaSymeProtocol(TForm exporter, Syme syme);
643localstatic Foam gfjExportToJavaFn(ForeignOrigin forg, String clssName, TForm tf, Syme syme);
644
645/*
646 * AbSyn: export Foo to Foreign Java("aldor.types")
647 *
648 * FOAM_Proto_JavaType:
649 * (DDecl Globals
650 * (GDecl Word "aldor.types.Foo" JavaMethod)
651 * ...
652 * (Def (Glo n) (Clos 0 (const blah))
653 */
654
655void
656gfjExportToJava(AbSyn absyn, AbSyn dest)
657{
658 AbSyn name = abDefineeId(absyn);
659 Syme syme = abSyme(name)((name)->abHdr.seman ? (name)->abHdr.seman->syme : 0
)
;
1
Assuming field 'seman' is null
2
'?' condition is false
660 TForm tf;
661 Foam decl;
662 FoamTag rtype;
663 AInt index;
664 ForeignOrigin forg = forgFrAbSyn(abApplyArg(dest, 0)((dest)->abApply.argv[0]));
665
666 if (abIsId(absyn)((absyn)->abHdr.tag == (AB_Id)) && abSyme(absyn)((absyn)->abHdr.seman ? (absyn)->abHdr.seman->syme :
0)
!= NULL((void*)0)
) {
3
Assuming field 'tag' is equal to AB_Id
4
Assuming field 'seman' is non-null
5
'?' condition is true
6
Assuming the condition is true
7
Taking true branch
667 gfjExportToJavaClass(absyn, forg);
8
Calling 'gfjExportToJavaClass'
668 }
669 else {
670 bug("Unknown java export");
671 }
672}
673
674localstatic void
675gfjExportToJavaClass(AbSyn absyn, ForeignOrigin forg)
676{
677 TForm tf;
678 SymeList imports;
679 String clssName;
680
681 if (!abIsId(absyn)((absyn)->abHdr.tag == (AB_Id))) {
9
Taking false branch
682 return;
683 }
684
685 clssName = symString(abIdSym(absyn))((((absyn)->abId.sym))->str);
686
687 tf = tiGetTForm(stabFile(), absyn);
688 // Normal imports
689 imports = tfGetDomImports(tf);
690 while (imports != listNil(Syme)((SymeList) 0)) {
10
Assuming 'imports' is not equal to listNil(Syme)
11
Loop condition is true. Entering loop body
691 Syme import = car(imports)((imports)->first);
692 imports = cdr(imports)((imports)->rest);
693 if (tfJavaCanExport(gen0State->stab, tf, symeType(import))) {
12
Assuming the condition is true
13
Taking true branch
694 Foam clos = gfjExportToJavaFn(forg, clssName, tf, import);
695 gfjExportToJavaSyme(tf, import, clos);
14
Calling 'gfjExportToJavaSyme'
696 }
697 }
698
699 TQualList cascades = tfGetDomCascades(tf);
700 // Qualified imports
701 while (cascades != listNil(TQual)((TQualList) 0)) {
702 TQual tq = car(cascades)((cascades)->first);
703
704 // Currently, ignore imports from qualified sources
705 // - more code, and we only want toString at the moment.
706 if (tqIsQualified(tq)((tq)->isQual == 1)) continue;
707 SymeList sl = tfGetDomImports(tqBase(tq)((tq)->base));
708
709 while (sl != listNil(Syme)((SymeList) 0)) {
710 Syme import = car(sl)((sl)->first);
711 if (strEqual(symeString(import)((((import)->id))->str), "toString")
712 && tfJavaCanExport(gen0State->stab, tf, symeType(import))) {
713 Foam clos = gfjExportToJavaFn(forg, clssName, tf, import);
714 gfjExportToJavaSyme(tf, import, clos);
715 }
716 sl = cdr(sl)((sl)->rest);
717 }
718 cascades = cdr(cascades)((cascades)->rest);
719 }
720}
721
722localstatic void
723gfjExportToJavaSyme(TForm exporter, Syme syme, Foam clos)
724{
725 TForm tf = symeType(syme);
726 Foam decl;
727 AInt index;
728
729 assert(syme)do { if (!(syme)) _do_assert(("syme"),"gf_java.c",729); } while
(0)
;
15
Taking false branch
16
Loop condition is false. Exiting loop
730
731 if (!tfIsMap(tf)(((tf)->tag) == TF_Map))
17
Assuming field 'tag' is equal to TF_Map
18
Taking false branch
732 return;
733
734 /* Generate a java style function matching this symbol's type */
735 ForeignOrigin forg = stabForeignExportLocation(gen0State->stab, exporter);
736 AInt protocol = gfjExportToJavaSymeProtocol(exporter, syme);
737 AInt declFmt = gfjPCallDeclExport(tf, protocol);
738 AInt rtype = gen0Type(tfMapRet(tf)tfFollowArg(tf, 1), NULL((void*)0));
739 String methodName = gfjExportToJavaSymeMethodName(syme);
740 String foamName = gfjDeclMethodName(symeString(tfIdSyme(exporter))((((((((exporter)->__absyn))->abHdr.seman ? (((exporter
)->__absyn))->abHdr.seman->syme : 0))->id))->str
)
, forg, methodName);
19
Assuming field 'seman' is null
20
'?' condition is false
21
Access to field 'id' results in a dereference of a null pointer
741
742 strFree(methodName);
743 decl = foamNewGDecl(FOAM_Clos, foamName, rtype,foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),foamName, rtype,declFmt
, (AInt)(FOAM_GDecl_Export),(AInt)(protocol))
744 declFmt, FOAM_GDecl_Export, protocol)foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),foamName, rtype,declFmt
, (AInt)(FOAM_GDecl_Export),(AInt)(protocol))
;
745
746 index = gen0AddGlobal(decl);
747 gen0BuiltinExports = listCons(AInt)(AInt_listPointer->Cons)(index, gen0BuiltinExports);
748 gen0BuiltinExports = listCons(AInt)(AInt_listPointer->Cons)(int0((int) 0), gen0BuiltinExports);
749
750 gen0AddStmt(foamNewSet(foamNewGlo(index), clos)foamNew(FOAM_Set, 2, foamNew(FOAM_Glo, 1, (AInt)(index)), clos
)
, NULL((void*)0));
751}
752
753localstatic AInt
754gfjExportToJavaSymeProtocol(TForm exporter, Syme syme)
755{
756 TForm tf = symeType(syme);
757 assert(tfIsMap(tf))do { if (!((((tf)->tag) == TF_Map))) _do_assert(("tfIsMap(tf)"
),"gf_java.c",757); } while (0)
;
758 assert(symeIsImport(syme))do { if (!((((((syme)->kind == SYME_Trigger ? libGetAllSymes
((syme)->lib) : ((void*)0)), (syme))->kind) == SYME_Import
))) _do_assert(("symeIsImport(syme)"),"gf_java.c",758); } while
(0)
;
759
760 if (tfMapRetc(tf) == 1
761 && symeId(syme)((syme)->id) == ssymTheNew
762 && tfEqual(exporter, tfMapRetN(tf, 0))) {
763 return FOAM_Proto_JavaConstructor;
764 }
765 else if (tfMapArgc(tf) > 0 && tfEqual(exporter, tfMapArgN(tf, 0))) {
766 return FOAM_Proto_JavaMethod;
767 }
768 else {
769 return FOAM_Proto_Java;
770 }
771}
772
773
774localstatic String
775gfjExportToJavaSymeMethodName(Syme syme)
776{
777 TForm fullType = symeType(syme);
778 TForm type = tfMapArgc(fullType) == 0 ? tfNone()tfMulti(0) : tfMapRetN(fullType, 0);
779 String name = symeString(syme)((((syme)->id))->str);
780
781 if (name[strLength(name) - 1] == '?'
782 && tfEqual(type, tfBoolean)) {
783 name = strPrintf("is%c%s", toupper(name[0])(__uppercase[(name[0])+1]), name+1);
784 name[strLength(name)-1] = '\0';
785 }
786 if (strEqual(name, "=")) {
787 return strCopy("equals");
788 }
789
790 if (strEqual(name, "~=")) {
791 return strCopy("notEquals");
792 }
793
794 return strCopy(name);
795}
796
797localstatic Foam
798gfjExportToJavaFn(ForeignOrigin forg, String clssName, TForm this, Syme syme)
799{
800 GenFoamState saved;
801 FoamList args;
802 TForm tf;
803 Foam prog, clos;
804 String fnName;
805 AInt index;
806 int i;
807
808 AInt protocol = gfjExportToJavaSymeProtocol(this, syme);
809
810 tf = symeType(syme);
811 fnName = aStrPrintf("%s-wrapper", symeString(syme)((((syme)->id))->str));
812 clos = gen0ProgClosEmpty();
813 prog = gen0ProgInitEmpty(fnName, NULL((void*)0));
814 index = car(gen0State->envFormatStack)((gen0State->envFormatStack)->first);
815 saved = gen0ProgSaveState(PT_ExFn);
816
817 /*
818 * Generate a method which calls the syme, with args matching outer.
819 * Idea is that this can (probably) be inlined away.
820 */
821
822 for (i=0; i<tfMapArgc(tf); i++) {
823 TForm tfi = gfjPCallArgBaseJavaType(tfMapArgN(tf, i));
824 Foam decl = tfEqual(tfi, this)
825 ? gj0ClassDecl(forg, clssName)
826 : gfjPCallDeclArg(tfi);
827 gen0AddParam(decl);
828 }
829
830 args = listNil(Foam)((FoamList) 0);
831 for (i=0; i<tfMapArgc(tf); i++) {
832 TForm tfi = tfMapArgN(tf, i);
833 Foam foam;
834 if (tfEqual(tfi, this)) {
835 foam = foamNewPCall(FOAM_Proto_JavaMethod,
836 FOAM_Word,
837 gen0CharArray("rep"), foamNewPar(i)foamNew(FOAM_Par, 1, (AInt)(i)), NULL((void*)0));
838 }
839 else if (stabIsForeignExport(gen0State->stab, tfi)) {
840 foam = foamNewPCall(FOAM_Proto_JavaMethod,
841 FOAM_Word,
842 gen0CharArray("rep"), foamNewPar(i)foamNew(FOAM_Par, 1, (AInt)(i)), NULL((void*)0));
843 }
844 else {
845 foam = gfjPCallJavaToFoam(tfi, foamNewPar(i)foamNew(FOAM_Par, 1, (AInt)(i)));
846 }
847 args = listCons(Foam)(Foam_listPointer->Cons)(foam, args);
848 }
849 args = listNReverse(Foam)(Foam_listPointer->NReverse)(args);
850
851 TForm retTf = tfMapRet(tf)tfFollowArg(tf, 1);
852 FoamTag retType = gen0Type(retTf, NULL((void*)0));
853 Foam ccall = foamNewCCallOfList(retType, gen0Syme(syme), args);
854
855 Foam retVal;
856 AInt fmt;
857 FoamTag type;
858
859 retTf = tfIgnoreExceptions(retTf);
860 if (protocol == FOAM_Proto_JavaConstructor) {
861 type = FOAM_Word;
862 fmt = emptyFormatSlot4;
863 gen0AddStmt(foamNewReturn(ccall)foamNew(FOAM_Return, 1, ccall), NULL((void*)0));
864 }
865 else if (tfIsNone(retTf)((((retTf)->tag) == TF_Multiple) && tfMultiArgc(retTf
) == 0)
) {
866 gen0AddStmt(ccall, NULL((void*)0));
867 type = FOAM_NOp;
868 fmt = emptyFormatSlot4;
869 }
870 else if (tfEqual(retTf, this)) {
871 retVal = foamNewPCall(FOAM_Proto_JavaConstructor, FOAM_JavaObj,
872 gen0CharArray(gfjDeclClassName(clssName, forg)),
873 ccall, NULL((void*)0));
874 Foam retDecl = gj0ClassDecl(forg, clssName);
875 type = retDecl->foamDecl.type;
876 fmt = retDecl->foamDecl.format;
877 gen0AddStmt(foamNewReturn(retVal)foamNew(FOAM_Return, 1, retVal), NULL((void*)0));
878 }
879 else if (stabIsForeignExport(gen0State->stab, retTf)) {
880 ForeignOrigin forgRet = stabForeignExportLocation(gen0State->stab, retTf);
881 type = gfjPCallFoamType(retTf, &fmt);
882
883 retVal = foamNewPCall(FOAM_Proto_JavaConstructor, FOAM_JavaObj,
884 gen0CharArray(gfjDeclClassName(symeString(tfIdSyme(retTf))((((((((retTf)->__absyn))->abHdr.seman ? (((retTf)->
__absyn))->abHdr.seman->syme : 0))->id))->str)
, forgRet)),
885 ccall, NULL((void*)0));
886 gen0AddStmt(foamNewReturn(retVal)foamNew(FOAM_Return, 1, retVal), NULL((void*)0));
887 }
888 else {
889 Foam retVal = gfjPCallFoamToJava(retTf, ccall);
890 type = gfjPCallFoamType(retTf, &fmt);
891 gen0AddStmt(foamNewReturn(retVal)foamNew(FOAM_Return, 1, retVal), NULL((void*)0));
892 }
893
894 gen0ProgPushFormat(emptyFormatSlot4);
895
896 gen0ProgFiniEmpty(prog, type, fmt);
897 gen0AddLexLevels(prog, 1);
898
899 foamOptInfo(prog)((prog)->hdr.info.opt) = optInfoNew(NULL((void*)0), prog, NULL((void*)0), false((int) 0));
900 gen0ProgRestoreState(saved);
901
902 return clos;
903}
904
905/*
906 * :: Utils
907 */
908
909localstatic String
910gfjDeclMethodNameForType(TForm tf, String methodName)
911{
912 assert(tfIsApply(tf) || tfIsId(tf))do { if (!(((((tf)->tag) == TF_General) && ((((tf)
->__absyn))->abHdr.tag) == AB_Apply) || ((((tf)->tag
) == TF_General) && ((((tf)->__absyn))->abHdr.tag
) == AB_Id))) _do_assert(("tfIsApply(tf) || tfIsId(tf)"),"gf_java.c"
,912); } while (0)
;
913
914 Syme esyme = tfIsApply(tf)((((tf)->tag) == TF_General) && ((((tf)->__absyn
))->abHdr.tag) == AB_Apply)
915 ? abSyme(tfExpr(tf)->abApply.op)((tfToAbSyn(tf)->abApply.op)->abHdr.seman ? (tfToAbSyn(
tf)->abApply.op)->abHdr.seman->syme : 0)
916 : tfIdSyme(tf)((((tf)->__absyn))->abHdr.seman ? (((tf)->__absyn))->
abHdr.seman->syme : 0)
;
917 ForeignOrigin forg = symeForeign(esyme)((ForeignOrigin) (SYFI_Foreign < (8 * sizeof(int)) &&
!(((((esyme)->kind == SYME_Trigger ? libGetAllSymes((esyme
)->lib) : ((void*)0)), (esyme))->hasmask) & (1 <<
(SYFI_Foreign))) ? (symeFieldInfo[SYFI_Foreign].def) : (((((
esyme)->kind == SYME_Trigger ? libGetAllSymes((esyme)->
lib) : ((void*)0)), (esyme))->locmask) & (1 << (
SYFI_Foreign))) ? ((((((esyme)->kind == SYME_Trigger ? libGetAllSymes
((esyme)->lib) : ((void*)0)), (esyme))->locmask) & (
1 << (SYFI_Foreign))) ? ((esyme)->fieldv)[symeIndex(
esyme,SYFI_Foreign)] : (symeFieldInfo[SYFI_Foreign].def)) : symeGetFieldFn
(esyme,SYFI_Foreign)))
;
918
919 return gfjDeclMethodName(symeString(esyme)((((esyme)->id))->str), forg, methodName);
920}
921
922localstatic String
923gfjDeclMethodName(String typeName, ForeignOrigin forg, String methodName)
924{
925 String name = forg->file
926 ? strPrintf("%s.%s.%s", forg->file, typeName, methodName)
927 : strPrintf("%s.%s", typeName, methodName);
928 return name;
929}
930
931localstatic String
932gfjDeclClassNameForType(TForm tf)
933{
934 assert(tfIsApply(tf) || tfIsId(tf))do { if (!(((((tf)->tag) == TF_General) && ((((tf)
->__absyn))->abHdr.tag) == AB_Apply) || ((((tf)->tag
) == TF_General) && ((((tf)->__absyn))->abHdr.tag
) == AB_Id))) _do_assert(("tfIsApply(tf) || tfIsId(tf)"),"gf_java.c"
,934); } while (0)
;
935
936 Syme esyme = tfIsApply(tf)((((tf)->tag) == TF_General) && ((((tf)->__absyn
))->abHdr.tag) == AB_Apply)
937 ? abSyme(tfExpr(tf)->abApply.op)((tfToAbSyn(tf)->abApply.op)->abHdr.seman ? (tfToAbSyn(
tf)->abApply.op)->abHdr.seman->syme : 0)
938 : tfIdSyme(tf)((((tf)->__absyn))->abHdr.seman ? (((tf)->__absyn))->
abHdr.seman->syme : 0)
;
939 ForeignOrigin forg = symeForeign(esyme)((ForeignOrigin) (SYFI_Foreign < (8 * sizeof(int)) &&
!(((((esyme)->kind == SYME_Trigger ? libGetAllSymes((esyme
)->lib) : ((void*)0)), (esyme))->hasmask) & (1 <<
(SYFI_Foreign))) ? (symeFieldInfo[SYFI_Foreign].def) : (((((
esyme)->kind == SYME_Trigger ? libGetAllSymes((esyme)->
lib) : ((void*)0)), (esyme))->locmask) & (1 << (
SYFI_Foreign))) ? ((((((esyme)->kind == SYME_Trigger ? libGetAllSymes
((esyme)->lib) : ((void*)0)), (esyme))->locmask) & (
1 << (SYFI_Foreign))) ? ((esyme)->fieldv)[symeIndex(
esyme,SYFI_Foreign)] : (symeFieldInfo[SYFI_Foreign].def)) : symeGetFieldFn
(esyme,SYFI_Foreign)))
;
940
941 return gfjDeclClassName(symeString(esyme)((((esyme)->id))->str), forg);
942}
943
944localstatic String
945gfjDeclClassName(String typeName, ForeignOrigin forg)
946{
947 String name = forg->file
948 ? strPrintf("%s.%s", forg->file, typeName)
949 : strCopy(typeName);
950 return name;
951}
952
953localstatic AInt
954gfjExportDecoder(TForm tf)
955{
956 Foam gdecl;
957 AInt cached;
958
959 cached = (AInt) tblElt(gfjExportDecoderForTForm, (TblKey) tf, (TblElt) -1);
960 if (cached != -1) {
961 return cached;
962 }
963 // Need a global that converts a java object to tf.
964 // This will be <object>.rep()
965 String globName = gfjDeclMethodName(symeString(tfIdSyme(tf))((((((((tf)->__absyn))->abHdr.seman ? (((tf)->__absyn
))->abHdr.seman->syme : 0))->id))->str)
,
966 stabForeignExportLocation(gen0State->stab, tf),
967 "rep");
968
969 Foam ddecl = javaSigNew(foamNewDecl(FOAM_Word, strCopy(""), emptyFormatSlot)foamNew(FOAM_Decl,4,(AInt)(FOAM_Word),strCopy(""), (AInt) (0x7FFF
), 4)
,
970 foamNewDecl(FOAM_NOp, strCopy(""), emptyFormatSlot)foamNew(FOAM_Decl,4,(AInt)(FOAM_NOp),strCopy(""), (AInt) (0x7FFF
), 4)
,
971 listSingleton(Foam)(Foam_listPointer->Singleton)(gfjPCallDeclArg(tf)));
972 AInt sigIdx = gen0AddRealFormat(ddecl);
973 gdecl = foamNewGDecl(FOAM_Clos, globName, FOAM_Nil, sigIdx,foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,sigIdx
, (AInt)(FOAM_GDecl_Import),(AInt)(FOAM_Proto_JavaMethod))
974 FOAM_GDecl_Import, FOAM_Proto_JavaMethod)foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,sigIdx
, (AInt)(FOAM_GDecl_Import),(AInt)(FOAM_Proto_JavaMethod))
;
975
976 AInt idx = gen0AddGlobal(gdecl);
977
978 tblSetElt(gfjExportDecoderForTForm, (TblKey) tf, (TblElt) idx);
979
980 return idx;
981}
982
983localstatic AInt
984gfjExportEncoder(TForm tf)
985{
986 Foam gdecl;
987 AInt cached;
988
989 cached = (AInt) tblElt(gfjExportEncoderForTForm, (TblKey) tf, (TblElt) -1);
990 if (cached != -1) {
991 return cached;
992 }
993 // Need a global that converts a tf to a java object
994 // This will be new <X>();
995 String globName = gfjDeclClassName(symeString(tfIdSyme(tf))((((((((tf)->__absyn))->abHdr.seman ? (((tf)->__absyn
))->abHdr.seman->syme : 0))->id))->str)
, stabForeignExportLocation(gen0State->stab, tf));
996
997 Foam ddecl = javaSigNew(gfjPCallDeclArg(tf),
998 foamNewDecl(FOAM_NOp, strCopy(""), emptyFormatSlot)foamNew(FOAM_Decl,4,(AInt)(FOAM_NOp),strCopy(""), (AInt) (0x7FFF
), 4)
,
999 listSingleton(Foam)(Foam_listPointer->Singleton)(foamNewDecl(FOAM_Word, strCopy(""), emptyFormatSlot)foamNew(FOAM_Decl,4,(AInt)(FOAM_Word),strCopy(""), (AInt) (0x7FFF
), 4)
));
1000 AInt sigIdx = gen0AddRealFormat(ddecl);
1001
1002 gdecl = foamNewGDecl(FOAM_Clos, globName, FOAM_Nil, sigIdx,foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,sigIdx
, (AInt)(FOAM_GDecl_Import),(AInt)(FOAM_Proto_JavaMethod))
1003 FOAM_GDecl_Import, FOAM_Proto_JavaMethod)foamNew(FOAM_GDecl,6,(AInt)(FOAM_Clos),globName, FOAM_Nil,sigIdx
, (AInt)(FOAM_GDecl_Import),(AInt)(FOAM_Proto_JavaMethod))
;
1004
1005 AInt idx = gen0AddGlobal(gdecl);
1006
1007 tblSetElt(gfjExportEncoderForTForm, (TblKey) tf, (TblElt) idx);
1008
1009 return idx;
1010}