fez-lisp 1.6.39 → 1.6.40

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/src/check.js +60 -9
package/package.json CHANGED
@@ -2,7 +2,7 @@
2
2
  "name": "fez-lisp",
3
3
  "description": "Lisp interpreted & compiled to JavaScript",
4
4
  "author": "AT290690",
5
- "version": "1.6.39",
5
+ "version": "1.6.40",
6
6
  "type": "module",
7
7
  "main": "index.js",
8
8
  "keywords": [
package/src/check.js CHANGED
@@ -1204,26 +1204,77 @@ export const typeCheck = (
1204
1204
  )
1205
1205
  // TODO check let define types
1206
1206
  const name = rest[0][VALUE]
1207
- if (env.hasOwnProperty(name))
1207
+ if (name[0] !== PLACEHOLDER && env.hasOwnProperty(name))
1208
1208
  throw new ReferenceError(
1209
1209
  `Attempting to redeclare (${name}) which was previously declared in this scope (${stringifyArgs(
1210
1210
  exp
1211
1211
  )})`
1212
1212
  )
1213
+ const rightHand = rest.at(-1)
1214
+ const isApply =
1215
+ rightHand && rightHand[0] && rightHand[0][TYPE] === APPLY
1216
+ const isLambda =
1217
+ isApply && rightHand[0][VALUE] === KEYWORDS.ANONYMOUS_FUNCTION
1213
1218
  if (name in env) {
1214
- typeSet(Types, name, env, exp)
1215
1219
  // Types.set(withScope(name, env), () => formatType(name, env))
1216
1220
  // If current scope is root then these are user defined types
1221
+ if (isLambda && !isUnknownReturn(env[name][STATS])) {
1222
+ const lambdaName = `${PLACEHOLDER}${ANONYMOUS_FUNCTION_TYPE_PREFIX}${rootScopeIndex}`
1223
+ check(
1224
+ [
1225
+ [APPLY, KEYWORDS.DEFINE_VARIABLE],
1226
+ [WORD, lambdaName],
1227
+ exp.at(-1)
1228
+ ],
1229
+ env,
1230
+ scope
1231
+ )
1232
+ const expected = env[name]
1233
+ const actual = env[lambdaName]
1234
+ once(actual[STATS], exp, stack, () => {
1235
+ if (
1236
+ !isUnknownReturn(actual[STATS]) &&
1237
+ (!equalReturns(expected[STATS], actual[STATS]) ||
1238
+ !equalSubReturns(expected[STATS], actual[STATS]))
1239
+ )
1240
+ throw new TypeError(
1241
+ `Incorrect return type for (${
1242
+ expected[STATS][SIGNATURE]
1243
+ }) Expected (${formatSubType(
1244
+ getReturns(expected[STATS])
1245
+ )}) but got (${formatSubType(
1246
+ getReturns(actual[STATS])
1247
+ )}) (${stringifyArgs(exp)}) (check #999)`
1248
+ )
1249
+ for (let i = 0; i < expected[STATS][ARGUMENTS].length; ++i) {
1250
+ const argE = expected[STATS][ARGUMENTS][i]
1251
+ const argA = actual[STATS][ARGUMENTS][i]
1252
+ if (
1253
+ !isUnknownType(argA[STATS]) &&
1254
+ (!equalTypes(argE[STATS], argA[STATS]) ||
1255
+ !equalSubTypes(argE[STATS], argA[STATS]))
1256
+ )
1257
+ throw new TypeError(
1258
+ `Incorrect return type for argument (${
1259
+ argA[STATS][SIGNATURE]
1260
+ }) The (${KEYWORDS.ANONYMOUS_FUNCTION}) argument of (${
1261
+ expected[STATS][SIGNATURE]
1262
+ }) at position (${i}). Expected (${formatSubType(
1263
+ getTypes(argE[STATS])
1264
+ )}) but got (${formatSubType(
1265
+ getTypes(argA[STATS])
1266
+ )}) (${stringifyArgs(exp)}) (check #1000)`
1267
+ )
1268
+ }
1269
+
1270
+ Types.delete(`; ${rootScopeIndex} ${lambdaName}`)
1271
+ })
1272
+ }
1273
+ typeSet(Types, name, env, exp)
1217
1274
  if (env[SCOPE_NAME] === rootScopeIndex) break
1218
1275
  }
1219
1276
  // Predicate name consistency
1220
- const rightHand = rest.at(-1)
1221
- const isApply =
1222
- rightHand && rightHand[0] && rightHand[0][TYPE] === APPLY
1223
- if (
1224
- isApply &&
1225
- rightHand[0][VALUE] === KEYWORDS.ANONYMOUS_FUNCTION
1226
- ) {
1277
+ if (isLambda) {
1227
1278
  validateLambda(rightHand, name)
1228
1279
  const n = rightHand.length
1229
1280
  env[name] = {