@mintplayer/polyglot-target-php 0.5.1 → 0.5.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (2) hide show
  1. package/package.json +1 -1
  2. package/polyglot-plugin.json +1089 -91
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@mintplayer/polyglot-target-php",
3
- "version": "0.5.1",
3
+ "version": "0.5.3",
4
4
  "description": "MintPlayer Polyglot PHP target — a pure-JSON language plugin (spec + emission rules + capabilities + std bindings) for the polyglot transpiler.",
5
5
  "keywords": [
6
6
  "polyglot",
@@ -2,14 +2,15 @@
2
2
  "schema": 1,
3
3
  "name": "php",
4
4
  "capabilities": {
5
- "patternMatching": false,
6
- "withExpressions": false,
5
+ "patternMatching": "native",
6
+ "withExpressions": "native",
7
+ "properties": "emulated",
7
8
  "async": false,
8
- "closures": false,
9
- "exceptions": false,
10
- "interfaces": false,
11
- "blockLambdas": false,
12
- "extensionMethods": false,
9
+ "closures": "native",
10
+ "exceptions": "native",
11
+ "interfaces": "native",
12
+ "blockLambdas": "native",
13
+ "extensionMethods": "emulated",
13
14
  "operatorOverloading": false
14
15
  },
15
16
  "spec": {
@@ -28,6 +29,7 @@
28
29
  "stmtEnd": ";",
29
30
  "throwKeyword": "throw",
30
31
  "rethrow": "throw $__e;",
32
+ "memberOp": "->",
31
33
  "trueLit": "true",
32
34
  "falseLit": "false",
33
35
  "nullLit": "null",
@@ -140,6 +142,10 @@
140
142
  "strategy": "suffix",
141
143
  "with": "_"
142
144
  },
145
+ "mangle": {
146
+ "replace": "$",
147
+ "with": "_"
148
+ },
143
149
  "reserved": [
144
150
  "__e",
145
151
  "__opt*",
@@ -149,11 +155,46 @@
149
155
  "preludes": {}
150
156
  },
151
157
  "std": {
158
+ "std.collections": {
159
+ "List.type": "array",
160
+ "List.init": "[]",
161
+ "List.count": "count($this)",
162
+ "List.add": "$this[] = $0",
163
+ "List.clear": "$this = []",
164
+ "List.removeAll": "$this = array_values(array_filter($this, fn($__e) => !(($0)($__e))))",
165
+ "List.removeAt": "array_splice($this, $0, 1)"
166
+ },
152
167
  "std.io": {
153
- "print": "echo is_bool($x) ? ($x ? \"true\" : \"false\") : $x, \"\\n\""
168
+ "print": "echo is_bool($x) ? ($x ? \"true\" : \"false\") : $x, \"\\n\"",
169
+ "readText": "file_get_contents($path)",
170
+ "writeText": "file_put_contents($path, $content)",
171
+ "appendText": "file_put_contents($path, $content, FILE_APPEND)",
172
+ "fileExists": "file_exists($path)",
173
+ "deleteFile": "unlink($path)"
174
+ },
175
+ "std.strings": {
176
+ "string.isEmpty": "($this === '')",
177
+ "string.len": "strlen($this)",
178
+ "string.toUpper": "strtoupper($this)",
179
+ "string.toLower": "strtolower($this)",
180
+ "string.charAt": "substr($this, $0, 1)",
181
+ "string.codePoints": "str_split($this)",
182
+ "string.toI32": "intval($this)"
154
183
  },
155
184
  "std.core": {
156
- "i32.parse": "(intval($0) & 0xffffffff)",
185
+ "Error.type": "\\Exception",
186
+ "Error.init": "new $T($0)",
187
+ "Error.message": "$this->getMessage()",
188
+ "Iterable.type": "iterable",
189
+ "i8.parse": "intval($0)",
190
+ "i16.parse": "intval($0)",
191
+ "i32.parse": "intval($0)",
192
+ "i64.parse": "intval($0)",
193
+ "u8.parse": "intval($0)",
194
+ "u16.parse": "intval($0)",
195
+ "u32.parse": "intval($0)",
196
+ "u64.parse": "intval($0)",
197
+ "f32.parse": "floatval($0)",
157
198
  "f64.parse": "floatval($0)"
158
199
  },
159
200
  "std.math": {
@@ -245,10 +286,21 @@
245
286
  "Call": {
246
287
  "tmpl": [
247
288
  {
248
- "fn": "ident",
289
+ "case": {
290
+ "when": [ [ { "eq": ["node.isFree", "true"] }, "" ] ],
291
+ "else": "$"
292
+ }
293
+ },
294
+ {
295
+ "fn": "mangleName",
249
296
  "args": [
250
297
  {
251
- "get": "node.mangledCallee"
298
+ "fn": "ident",
299
+ "args": [
300
+ {
301
+ "get": "node.mangledCallee"
302
+ }
303
+ ]
252
304
  }
253
305
  ]
254
306
  },
@@ -312,12 +364,76 @@
312
364
  "get": "node.field"
313
365
  }
314
366
  ]
367
+ },
368
+ {
369
+ "case": {
370
+ "when": [
371
+ [
372
+ {
373
+ "eq": [
374
+ "node.isProperty",
375
+ "true"
376
+ ]
377
+ },
378
+ "()"
379
+ ]
380
+ ]
381
+ }
315
382
  }
316
383
  ]
317
384
  },
318
385
  "MethodCall": {
319
386
  "case": {
320
387
  "when": [
388
+ [
389
+ {
390
+ "eq": [
391
+ "node.isExtension",
392
+ "true"
393
+ ]
394
+ },
395
+ {
396
+ "tmpl": [
397
+ {
398
+ "fn": "ident",
399
+ "args": [
400
+ {
401
+ "get": "node.method"
402
+ }
403
+ ]
404
+ },
405
+ "(",
406
+ {
407
+ "emit": "node.object"
408
+ },
409
+ {
410
+ "case": {
411
+ "when": [
412
+ [
413
+ {
414
+ "eq": [
415
+ "node.args.count",
416
+ "0"
417
+ ]
418
+ },
419
+ ""
420
+ ]
421
+ ],
422
+ "else": {
423
+ "tmpl": [
424
+ ", ",
425
+ {
426
+ "map": "node.args",
427
+ "sep": ", "
428
+ }
429
+ ]
430
+ }
431
+ }
432
+ },
433
+ ")"
434
+ ]
435
+ }
436
+ ],
321
437
  [
322
438
  {
323
439
  "has": "node.staticType"
@@ -448,6 +564,48 @@
448
564
  "]"
449
565
  ]
450
566
  },
567
+ "Lambda": {
568
+ "case": {
569
+ "when": [
570
+ [
571
+ { "and": [ { "eq": ["node.exprBodied", "true"] }, { "eq": ["node.allCapturesByValue", "true"] } ] },
572
+ { "tmpl": [
573
+ "fn(",
574
+ { "map": "node.params", "sep": ", ", "item": { "tmpl": ["$", { "fn": "ident", "args": [ { "get": "item.name" } ] } ] } },
575
+ ") => ",
576
+ { "emit": "node.body" }
577
+ ] }
578
+ ]
579
+ ],
580
+ "else": { "tmpl": [
581
+ "function (",
582
+ { "map": "node.params", "sep": ", ", "item": { "tmpl": ["$", { "fn": "ident", "args": [ { "get": "item.name" } ] } ] } },
583
+ ")",
584
+ { "case": {
585
+ "when": [
586
+ [
587
+ { "not": { "eq": ["node.captures.count", "0"] } },
588
+ { "tmpl": [
589
+ " use (",
590
+ { "map": "node.captures", "sep": ", ", "item": { "tmpl": [
591
+ { "case": { "when": [ [ { "eq": ["item.needsCell", "true"] }, "&$" ] ], "else": "$" } },
592
+ { "fn": "ident", "args": [ { "get": "item.name" } ] }
593
+ ] } },
594
+ ")"
595
+ ] }
596
+ ]
597
+ ],
598
+ "else": ""
599
+ } },
600
+ " { ",
601
+ { "case": {
602
+ "when": [ [ { "eq": ["node.exprBodied", "true"] }, { "tmpl": ["return ", { "emit": "node.body" }, ";"] } ] ],
603
+ "else": { "fn": "inlineBlock" }
604
+ } },
605
+ " }"
606
+ ] }
607
+ }
608
+ },
451
609
  "New": {
452
610
  "tmpl": [
453
611
  "new ",
@@ -821,58 +979,701 @@
821
979
  }
822
980
  }
823
981
  },
824
- "Type": {
825
- "case": {
826
- "when": [
827
- [
828
- {
829
- "has": "type.externTemplate"
830
- },
831
- {
832
- "fn": "substExtern"
982
+ "TryStmt": {
983
+ "seq": [
984
+ {
985
+ "block": {
986
+ "head": "try",
987
+ "body": [
988
+ {
989
+ "stmts": "stmt.body"
990
+ }
991
+ ]
992
+ }
993
+ },
994
+ {
995
+ "mapDecl": "stmt.catches",
996
+ "each": {
997
+ "block": {
998
+ "head": {
999
+ "tmpl": [
1000
+ "catch (",
1001
+ {
1002
+ "case": {
1003
+ "when": [
1004
+ [
1005
+ {
1006
+ "eq": [
1007
+ "item.hasType",
1008
+ "true"
1009
+ ]
1010
+ },
1011
+ {
1012
+ "type": "item.type"
1013
+ }
1014
+ ]
1015
+ ],
1016
+ "else": "\\Throwable"
1017
+ }
1018
+ },
1019
+ " $__e)"
1020
+ ]
1021
+ },
1022
+ "body": [
1023
+ {
1024
+ "case": {
1025
+ "when": [
1026
+ [
1027
+ {
1028
+ "eq": [
1029
+ "item.hasBinding",
1030
+ "true"
1031
+ ]
1032
+ },
1033
+ {
1034
+ "line": {
1035
+ "tmpl": [
1036
+ "$",
1037
+ {
1038
+ "fn": "ident",
1039
+ "args": [
1040
+ {
1041
+ "get": "item.binding"
1042
+ }
1043
+ ]
1044
+ },
1045
+ " = $__e;"
1046
+ ]
1047
+ }
1048
+ }
1049
+ ]
1050
+ ]
1051
+ }
1052
+ },
1053
+ {
1054
+ "case": {
1055
+ "when": [
1056
+ [
1057
+ {
1058
+ "eq": [
1059
+ "item.hasGuard",
1060
+ "true"
1061
+ ]
1062
+ },
1063
+ {
1064
+ "line": {
1065
+ "tmpl": [
1066
+ "if (!(",
1067
+ {
1068
+ "emit": "item.guard"
1069
+ },
1070
+ ")) { throw $__e; }"
1071
+ ]
1072
+ }
1073
+ }
1074
+ ]
1075
+ ]
1076
+ }
1077
+ },
1078
+ {
1079
+ "stmts": "item.body"
1080
+ }
1081
+ ]
833
1082
  }
834
- ]
835
- ],
836
- "else": {
837
- "fn": "ident",
1083
+ }
1084
+ },
1085
+ {
1086
+ "case": {
1087
+ "when": [
1088
+ [
1089
+ {
1090
+ "eq": [
1091
+ "stmt.hasFinally",
1092
+ "true"
1093
+ ]
1094
+ },
1095
+ {
1096
+ "block": {
1097
+ "head": "finally",
1098
+ "body": [
1099
+ {
1100
+ "stmts": "stmt.finallyBody"
1101
+ }
1102
+ ]
1103
+ }
1104
+ }
1105
+ ]
1106
+ ]
1107
+ }
1108
+ }
1109
+ ]
1110
+ },
1111
+ "MakeCase": {
1112
+ "tmpl": [
1113
+ "[\"tag\" => ",
1114
+ {
1115
+ "fn": "escapeString",
838
1116
  "args": [
839
1117
  {
840
- "get": "type.name"
1118
+ "get": "node.caseName"
841
1119
  }
842
1120
  ]
843
- }
1121
+ },
1122
+ {
1123
+ "map": "node.fields",
1124
+ "sep": "",
1125
+ "item": {
1126
+ "tmpl": [
1127
+ ", ",
1128
+ {
1129
+ "fn": "escapeString",
1130
+ "args": [
1131
+ {
1132
+ "get": "item.name"
1133
+ }
1134
+ ]
1135
+ },
1136
+ " => ",
1137
+ {
1138
+ "emit": "item.value"
1139
+ }
1140
+ ]
1141
+ }
1142
+ },
1143
+ "]"
1144
+ ]
1145
+ },
1146
+ "UnionDecl": {
1147
+ "line": {
1148
+ "tmpl": [
1149
+ "// union ",
1150
+ {
1151
+ "fn": "ident",
1152
+ "args": [
1153
+ {
1154
+ "get": "decl.name"
1155
+ }
1156
+ ]
1157
+ },
1158
+ " -> tagged arrays: [\"tag\" => <case>, <field> => <value>, ...]"
1159
+ ]
844
1160
  }
845
1161
  },
846
- "ForStmt": {
1162
+ "Match": {
1163
+ "tmpl": [
1164
+ "(fn($_m) => match (true) { ",
1165
+ {
1166
+ "map": "node.arms",
1167
+ "sep": ", ",
1168
+ "item": {
1169
+ "tmpl": [
1170
+ {
1171
+ "call": "phpArmCond"
1172
+ },
1173
+ " => ",
1174
+ {
1175
+ "call": "phpArmValue"
1176
+ }
1177
+ ]
1178
+ }
1179
+ },
1180
+ " })(",
1181
+ {
1182
+ "emit": "node.scrutinee"
1183
+ },
1184
+ ")"
1185
+ ]
1186
+ },
1187
+ "phpArmValue": {
847
1188
  "case": {
848
1189
  "when": [
849
1190
  [
850
1191
  {
851
1192
  "eq": [
852
- "stmt.isRange",
853
- "true"
1193
+ "item.pattern.kind",
1194
+ "binding"
854
1195
  ]
855
1196
  },
856
1197
  {
857
- "block": {
858
- "head": {
859
- "tmpl": [
860
- "for ($",
861
- {
862
- "fn": "ident",
863
- "args": [
864
- {
865
- "get": "stmt.binding"
866
- }
867
- ]
868
- },
869
- " = ",
870
- {
871
- "emit": "stmt.rangeStart"
872
- },
873
- "; $",
1198
+ "tmpl": [
1199
+ "(fn($",
1200
+ {
1201
+ "fn": "ident",
1202
+ "args": [
874
1203
  {
875
- "fn": "ident",
1204
+ "get": "item.pattern.binding"
1205
+ }
1206
+ ]
1207
+ },
1208
+ ") => ",
1209
+ {
1210
+ "emit": "item.body"
1211
+ },
1212
+ ")($_m)"
1213
+ ]
1214
+ }
1215
+ ],
1216
+ [
1217
+ {
1218
+ "and": [
1219
+ {
1220
+ "eq": [
1221
+ "item.pattern.kind",
1222
+ "ctor"
1223
+ ]
1224
+ },
1225
+ {
1226
+ "not": {
1227
+ "eq": [
1228
+ "item.pattern.binders.count",
1229
+ "0"
1230
+ ]
1231
+ }
1232
+ }
1233
+ ]
1234
+ },
1235
+ {
1236
+ "tmpl": [
1237
+ "(fn(",
1238
+ {
1239
+ "map": "item.pattern.binders",
1240
+ "sep": ", ",
1241
+ "item": {
1242
+ "tmpl": [
1243
+ "$",
1244
+ {
1245
+ "fn": "ident",
1246
+ "args": [
1247
+ {
1248
+ "get": "item.binding"
1249
+ }
1250
+ ]
1251
+ }
1252
+ ]
1253
+ }
1254
+ },
1255
+ ") => ",
1256
+ {
1257
+ "emit": "item.body"
1258
+ },
1259
+ ")(",
1260
+ {
1261
+ "map": "item.pattern.binders",
1262
+ "sep": ", ",
1263
+ "item": {
1264
+ "tmpl": [
1265
+ "$_m[",
1266
+ {
1267
+ "fn": "escapeString",
1268
+ "args": [
1269
+ {
1270
+ "get": "item.field"
1271
+ }
1272
+ ]
1273
+ },
1274
+ "]"
1275
+ ]
1276
+ }
1277
+ },
1278
+ ")"
1279
+ ]
1280
+ }
1281
+ ]
1282
+ ],
1283
+ "else": {
1284
+ "emit": "item.body"
1285
+ }
1286
+ }
1287
+ },
1288
+ "phpArmGuard": {
1289
+ "case": {
1290
+ "when": [
1291
+ [
1292
+ {
1293
+ "eq": [
1294
+ "item.pattern.kind",
1295
+ "binding"
1296
+ ]
1297
+ },
1298
+ {
1299
+ "tmpl": [
1300
+ "(fn($",
1301
+ {
1302
+ "fn": "ident",
1303
+ "args": [
1304
+ {
1305
+ "get": "item.pattern.binding"
1306
+ }
1307
+ ]
1308
+ },
1309
+ ") => ",
1310
+ {
1311
+ "emit": "item.guard"
1312
+ },
1313
+ ")($_m)"
1314
+ ]
1315
+ }
1316
+ ],
1317
+ [
1318
+ {
1319
+ "and": [
1320
+ {
1321
+ "eq": [
1322
+ "item.pattern.kind",
1323
+ "ctor"
1324
+ ]
1325
+ },
1326
+ {
1327
+ "not": {
1328
+ "eq": [
1329
+ "item.pattern.binders.count",
1330
+ "0"
1331
+ ]
1332
+ }
1333
+ }
1334
+ ]
1335
+ },
1336
+ {
1337
+ "tmpl": [
1338
+ "(fn(",
1339
+ {
1340
+ "map": "item.pattern.binders",
1341
+ "sep": ", ",
1342
+ "item": {
1343
+ "tmpl": [
1344
+ "$",
1345
+ {
1346
+ "fn": "ident",
1347
+ "args": [
1348
+ {
1349
+ "get": "item.binding"
1350
+ }
1351
+ ]
1352
+ }
1353
+ ]
1354
+ }
1355
+ },
1356
+ ") => ",
1357
+ {
1358
+ "emit": "item.guard"
1359
+ },
1360
+ ")(",
1361
+ {
1362
+ "map": "item.pattern.binders",
1363
+ "sep": ", ",
1364
+ "item": {
1365
+ "tmpl": [
1366
+ "$_m[",
1367
+ {
1368
+ "fn": "escapeString",
1369
+ "args": [
1370
+ {
1371
+ "get": "item.field"
1372
+ }
1373
+ ]
1374
+ },
1375
+ "]"
1376
+ ]
1377
+ }
1378
+ },
1379
+ ")"
1380
+ ]
1381
+ }
1382
+ ]
1383
+ ],
1384
+ "else": {
1385
+ "emit": "item.guard"
1386
+ }
1387
+ }
1388
+ },
1389
+ "phpArmBase": {
1390
+ "case": {
1391
+ "when": [
1392
+ [
1393
+ {
1394
+ "eq": [
1395
+ "item.pattern.kind",
1396
+ "literal"
1397
+ ]
1398
+ },
1399
+ {
1400
+ "tmpl": [
1401
+ "$_m == ",
1402
+ {
1403
+ "emit": "item.pattern.literal"
1404
+ }
1405
+ ]
1406
+ }
1407
+ ],
1408
+ [
1409
+ {
1410
+ "eq": [
1411
+ "item.pattern.kind",
1412
+ "enumCase"
1413
+ ]
1414
+ },
1415
+ {
1416
+ "tmpl": [
1417
+ "$_m == ",
1418
+ {
1419
+ "get": "item.pattern.enumType"
1420
+ },
1421
+ "::",
1422
+ {
1423
+ "get": "item.pattern.enumCase"
1424
+ }
1425
+ ]
1426
+ }
1427
+ ],
1428
+ [
1429
+ {
1430
+ "eq": [
1431
+ "item.pattern.kind",
1432
+ "ctor"
1433
+ ]
1434
+ },
1435
+ {
1436
+ "tmpl": [
1437
+ "$_m[\"tag\"] == ",
1438
+ {
1439
+ "fn": "escapeString",
1440
+ "args": [
1441
+ {
1442
+ "get": "item.pattern.ctorCase"
1443
+ }
1444
+ ]
1445
+ }
1446
+ ]
1447
+ }
1448
+ ]
1449
+ ],
1450
+ "else": "true"
1451
+ }
1452
+ },
1453
+ "phpArmCond": {
1454
+ "case": {
1455
+ "when": [
1456
+ [
1457
+ {
1458
+ "eq": [
1459
+ "item.hasGuard",
1460
+ "false"
1461
+ ]
1462
+ },
1463
+ {
1464
+ "call": "phpArmBase"
1465
+ }
1466
+ ],
1467
+ [
1468
+ {
1469
+ "or": [
1470
+ {
1471
+ "eq": [
1472
+ "item.pattern.kind",
1473
+ "wildcard"
1474
+ ]
1475
+ },
1476
+ {
1477
+ "eq": [
1478
+ "item.pattern.kind",
1479
+ "binding"
1480
+ ]
1481
+ }
1482
+ ]
1483
+ },
1484
+ {
1485
+ "call": "phpArmGuard"
1486
+ }
1487
+ ]
1488
+ ],
1489
+ "else": {
1490
+ "tmpl": [
1491
+ {
1492
+ "call": "phpArmBase"
1493
+ },
1494
+ " && ",
1495
+ {
1496
+ "call": "phpArmGuard"
1497
+ }
1498
+ ]
1499
+ }
1500
+ }
1501
+ },
1502
+ "InterfaceDecl": {
1503
+ "block": {
1504
+ "head": {
1505
+ "tmpl": [
1506
+ "interface ",
1507
+ {
1508
+ "fn": "ident",
1509
+ "args": [
1510
+ {
1511
+ "get": "decl.name"
1512
+ }
1513
+ ]
1514
+ },
1515
+ {
1516
+ "case": {
1517
+ "when": [
1518
+ [
1519
+ {
1520
+ "eq": [
1521
+ "decl.bases.count",
1522
+ "0"
1523
+ ]
1524
+ },
1525
+ ""
1526
+ ]
1527
+ ],
1528
+ "else": {
1529
+ "tmpl": [
1530
+ " extends ",
1531
+ {
1532
+ "map": "decl.bases",
1533
+ "sep": ", ",
1534
+ "item": {
1535
+ "type": "item"
1536
+ }
1537
+ }
1538
+ ]
1539
+ }
1540
+ }
1541
+ }
1542
+ ]
1543
+ },
1544
+ "body": [
1545
+ {
1546
+ "mapDecl": "decl.methods",
1547
+ "each": {
1548
+ "line": {
1549
+ "tmpl": [
1550
+ "public function ",
1551
+ {
1552
+ "fn": "ident",
1553
+ "args": [
1554
+ {
1555
+ "get": "item.name"
1556
+ }
1557
+ ]
1558
+ },
1559
+ "(",
1560
+ {
1561
+ "map": "item.params",
1562
+ "sep": ", ",
1563
+ "item": {
1564
+ "call": "phpParam"
1565
+ }
1566
+ },
1567
+ ");"
1568
+ ]
1569
+ }
1570
+ }
1571
+ }
1572
+ ]
1573
+ }
1574
+ },
1575
+ "With": {
1576
+ "case": {
1577
+ "when": [
1578
+ [
1579
+ {
1580
+ "eq": [
1581
+ "node.baseIsSimple",
1582
+ "true"
1583
+ ]
1584
+ },
1585
+ {
1586
+ "tmpl": [
1587
+ "new ",
1588
+ {
1589
+ "get": "node.type"
1590
+ },
1591
+ "(",
1592
+ {
1593
+ "map": "node.ctorArgs",
1594
+ "sep": ", "
1595
+ },
1596
+ ")"
1597
+ ]
1598
+ }
1599
+ ]
1600
+ ],
1601
+ "else": {
1602
+ "tmpl": [
1603
+ "(fn($",
1604
+ {
1605
+ "get": "node.tempName"
1606
+ },
1607
+ ") => new ",
1608
+ {
1609
+ "get": "node.type"
1610
+ },
1611
+ "(",
1612
+ {
1613
+ "map": "node.ctorArgs",
1614
+ "sep": ", "
1615
+ },
1616
+ "))(",
1617
+ {
1618
+ "emit": "node.base"
1619
+ },
1620
+ ")"
1621
+ ]
1622
+ }
1623
+ }
1624
+ },
1625
+ "Type": {
1626
+ "case": {
1627
+ "when": [
1628
+ [
1629
+ {
1630
+ "has": "type.externTemplate"
1631
+ },
1632
+ {
1633
+ "fn": "substExtern"
1634
+ }
1635
+ ]
1636
+ ],
1637
+ "else": {
1638
+ "fn": "ident",
1639
+ "args": [
1640
+ {
1641
+ "get": "type.name"
1642
+ }
1643
+ ]
1644
+ }
1645
+ }
1646
+ },
1647
+ "ForStmt": {
1648
+ "case": {
1649
+ "when": [
1650
+ [
1651
+ {
1652
+ "eq": [
1653
+ "stmt.isRange",
1654
+ "true"
1655
+ ]
1656
+ },
1657
+ {
1658
+ "block": {
1659
+ "head": {
1660
+ "tmpl": [
1661
+ "for ($",
1662
+ {
1663
+ "fn": "ident",
1664
+ "args": [
1665
+ {
1666
+ "get": "stmt.binding"
1667
+ }
1668
+ ]
1669
+ },
1670
+ " = ",
1671
+ {
1672
+ "emit": "stmt.rangeStart"
1673
+ },
1674
+ "; $",
1675
+ {
1676
+ "fn": "ident",
876
1677
  "args": [
877
1678
  {
878
1679
  "get": "stmt.binding"
@@ -1028,10 +1829,15 @@
1028
1829
  "tmpl": [
1029
1830
  "function ",
1030
1831
  {
1031
- "fn": "ident",
1832
+ "fn": "mangle",
1032
1833
  "args": [
1033
1834
  {
1034
- "get": "decl.emitName"
1835
+ "fn": "ident",
1836
+ "args": [
1837
+ {
1838
+ "get": "decl.emitName"
1839
+ }
1840
+ ]
1035
1841
  }
1036
1842
  ]
1037
1843
  },
@@ -1046,16 +1852,130 @@
1046
1852
  ")"
1047
1853
  ]
1048
1854
  },
1049
- "FunctionDecl": {
1050
- "block": {
1051
- "head": {
1052
- "call": "phpFnSig"
1855
+ "phpFnBody": {
1856
+ "seq": [
1857
+ {
1858
+ "case": {
1859
+ "when": [
1860
+ [
1861
+ {
1862
+ "not": {
1863
+ "eq": [
1864
+ "decl.globalRefs.count",
1865
+ "0"
1866
+ ]
1867
+ }
1868
+ },
1869
+ {
1870
+ "line": {
1871
+ "tmpl": [
1872
+ "global ",
1873
+ {
1874
+ "map": "decl.globalRefs",
1875
+ "sep": ", ",
1876
+ "item": {
1877
+ "tmpl": [
1878
+ "$",
1879
+ {
1880
+ "get": "item"
1881
+ }
1882
+ ]
1883
+ }
1884
+ },
1885
+ ";"
1886
+ ]
1887
+ }
1888
+ }
1889
+ ]
1890
+ ]
1891
+ }
1053
1892
  },
1054
- "body": [
1055
- {
1056
- "stmts": "decl.body"
1893
+ {
1894
+ "case": {
1895
+ "when": [
1896
+ [
1897
+ {
1898
+ "eq": [
1899
+ "decl.exprBodied",
1900
+ "true"
1901
+ ]
1902
+ },
1903
+ {
1904
+ "line": {
1905
+ "tmpl": [
1906
+ "return ",
1907
+ {
1908
+ "emit": "decl.exprBody"
1909
+ },
1910
+ ";"
1911
+ ]
1912
+ }
1913
+ }
1914
+ ]
1915
+ ],
1916
+ "else": {
1917
+ "stmts": "decl.body"
1918
+ }
1057
1919
  }
1058
- ]
1920
+ }
1921
+ ]
1922
+ },
1923
+ "FunctionDecl": {
1924
+ "case": {
1925
+ "when": [
1926
+ [
1927
+ {
1928
+ "eq": [
1929
+ "decl.isPrelude",
1930
+ "true"
1931
+ ]
1932
+ },
1933
+ {
1934
+ "block": {
1935
+ "head": {
1936
+ "tmpl": [
1937
+ "if (!function_exists('",
1938
+ {
1939
+ "fn": "ident",
1940
+ "args": [
1941
+ {
1942
+ "get": "decl.emitName"
1943
+ }
1944
+ ]
1945
+ },
1946
+ "'))"
1947
+ ]
1948
+ },
1949
+ "body": [
1950
+ {
1951
+ "block": {
1952
+ "head": {
1953
+ "call": "phpFnSig"
1954
+ },
1955
+ "body": [
1956
+ {
1957
+ "call": "phpFnBody"
1958
+ }
1959
+ ]
1960
+ }
1961
+ }
1962
+ ]
1963
+ }
1964
+ }
1965
+ ]
1966
+ ],
1967
+ "else": {
1968
+ "block": {
1969
+ "head": {
1970
+ "call": "phpFnSig"
1971
+ },
1972
+ "body": [
1973
+ {
1974
+ "call": "phpFnBody"
1975
+ }
1976
+ ]
1977
+ }
1978
+ }
1059
1979
  }
1060
1980
  },
1061
1981
  "phpMethodSig": {
@@ -1308,6 +2228,34 @@
1308
2228
  ]
1309
2229
  ]
1310
2230
  }
2231
+ },
2232
+ {
2233
+ "case": {
2234
+ "when": [
2235
+ [
2236
+ {
2237
+ "not": {
2238
+ "eq": [
2239
+ "decl.ifaceBases.count",
2240
+ "0"
2241
+ ]
2242
+ }
2243
+ },
2244
+ {
2245
+ "tmpl": [
2246
+ " implements ",
2247
+ {
2248
+ "map": "decl.ifaceBases",
2249
+ "sep": ", ",
2250
+ "item": {
2251
+ "type": "item"
2252
+ }
2253
+ }
2254
+ ]
2255
+ }
2256
+ ]
2257
+ ]
2258
+ }
1311
2259
  }
1312
2260
  ]
1313
2261
  },
@@ -1316,56 +2264,98 @@
1316
2264
  "mapDecl": "decl.fields",
1317
2265
  "each": {
1318
2266
  "line": {
1319
- "tmpl": [
1320
- "public ",
1321
- {
1322
- "case": {
1323
- "when": [
1324
- [
2267
+ "case": {
2268
+ "when": [
2269
+ [
2270
+ {
2271
+ "and": [
1325
2272
  {
1326
2273
  "eq": [
1327
2274
  "item.isStatic",
1328
2275
  "true"
1329
2276
  ]
1330
2277
  },
1331
- "static "
2278
+ {
2279
+ "eq": [
2280
+ "item.isMutable",
2281
+ "false"
2282
+ ]
2283
+ }
1332
2284
  ]
1333
- ]
1334
- }
1335
- },
1336
- "$",
1337
- {
1338
- "fn": "ident",
1339
- "args": [
2285
+ },
1340
2286
  {
1341
- "get": "item.name"
1342
- }
1343
- ]
1344
- },
1345
- {
1346
- "case": {
1347
- "when": [
1348
- [
2287
+ "tmpl": [
2288
+ "const ",
1349
2289
  {
1350
- "eq": [
1351
- "item.hasInit",
1352
- "true"
2290
+ "fn": "ident",
2291
+ "args": [
2292
+ {
2293
+ "get": "item.name"
2294
+ }
1353
2295
  ]
1354
2296
  },
2297
+ " = ",
1355
2298
  {
1356
- "tmpl": [
1357
- " = ",
2299
+ "emit": "item.init"
2300
+ },
2301
+ ";"
2302
+ ]
2303
+ }
2304
+ ]
2305
+ ],
2306
+ "else": {
2307
+ "tmpl": [
2308
+ "public ",
2309
+ {
2310
+ "case": {
2311
+ "when": [
2312
+ [
1358
2313
  {
1359
- "emit": "item.init"
1360
- }
2314
+ "eq": [
2315
+ "item.isStatic",
2316
+ "true"
2317
+ ]
2318
+ },
2319
+ "static "
1361
2320
  ]
2321
+ ]
2322
+ }
2323
+ },
2324
+ "$",
2325
+ {
2326
+ "fn": "ident",
2327
+ "args": [
2328
+ {
2329
+ "get": "item.name"
1362
2330
  }
1363
2331
  ]
1364
- ]
1365
- }
1366
- },
1367
- ";"
1368
- ]
2332
+ },
2333
+ {
2334
+ "case": {
2335
+ "when": [
2336
+ [
2337
+ {
2338
+ "eq": [
2339
+ "item.hasInit",
2340
+ "true"
2341
+ ]
2342
+ },
2343
+ {
2344
+ "tmpl": [
2345
+ " = ",
2346
+ {
2347
+ "emit": "item.init"
2348
+ }
2349
+ ]
2350
+ }
2351
+ ]
2352
+ ]
2353
+ }
2354
+ },
2355
+ ";"
2356
+ ]
2357
+ }
2358
+ }
1369
2359
  }
1370
2360
  }
1371
2361
  },
@@ -1462,6 +2452,10 @@
1462
2452
  "mapMembers": "module.records",
1463
2453
  "rule": "RecordDecl"
1464
2454
  },
2455
+ {
2456
+ "mapMembers": "module.interfaces",
2457
+ "rule": "InterfaceDecl"
2458
+ },
1465
2459
  {
1466
2460
  "mapMembers": "module.classes",
1467
2461
  "rule": "ClassDecl"
@@ -1508,6 +2502,10 @@
1508
2502
  "mapMembers": "module.functions",
1509
2503
  "rule": "FunctionDecl"
1510
2504
  },
2505
+ {
2506
+ "mapMembers": "module.extensions",
2507
+ "rule": "FunctionDecl"
2508
+ },
1511
2509
  {
1512
2510
  "case": {
1513
2511
  "when": [