shithub: sl

Download patch

ref: 6b4240737bd6f0f7337a4655c827148ebba17f02
parent: 530f3242a5795d0f25d7fe5c82fd112893c9ec09
author: Sigrid Solveig Haflínudóttir <sigrid@ftrv.se>
date: Thu Apr 17 16:17:24 EDT 2025

map: throw an error if passing invalid "resulting type"; better error messages

--- a/src/sl.c
+++ b/src/sl.c
@@ -1126,6 +1126,8 @@
 	bool rtdecl = true;
 	if(rt == sl_nil)
 		rtype = RT_NIL;
+	else if(rt == UNBOUND)
+		rtdecl = false;
 	else if(issym(rt)){
 		if(rt == sl_listsym)
 			rtype = RT_LIST;
@@ -1136,15 +1138,16 @@
 		else if(rt == sl_tablesym)
 			rtype = RT_TBL;
 		else
-			bthrow(type_error("sequence", rt));
+			bthrow(type_error("sequence type designator", rt));
 	}else if(iscons(rt)){
 		if(car_(rt) != sl_arrsym)
-			bthrow(type_error("sequence", rt));
+			bthrow(type_error("array type designator", rt));
 		rtype = RT_ARR;
 		arrtype = car_(cdr_(rt));
 		get_arr_type(arrtype);
-	}else
-		rtdecl = false;
+	}else{
+		bthrow(type_error("sequence type designator", rt));
+	}
 	sl_v *k = sl.sp;
 	PUSH(sl_nil);
 	PUSH(sl_nil);
@@ -1295,10 +1298,9 @@
 	if(sl_unlikely(nargs < 2))
 		argcount(nargs, 2);
 	sl_v v = args[0];
-	if(v == sl_nil || issym(v) || iscons(v))
-		return map_seq(v, args+1, nargs-1);
-	else
-		return map_seq(UNBOUND, args, nargs);
+	return isfn(v)
+		? map_seq(UNBOUND, args, nargs)
+		: map_seq(v, args+1, nargs-1);
 }
 
 BUILTIN("for-each", for_each)
--- a/test/unittest.sl
+++ b/test/unittest.sl
@@ -439,6 +439,9 @@
 (assert (equal? (map 'list + (vec 1 2 3) '(4 5 6)) '(5 7 9)))
 (assert (equal? (map 'str + (vec 1 2 3) '(4 5 6)) "579"))
 (assert (equal? (map '(arr s16) + (vec 1 2 3) '(4 5 6)) (arr 's16 5 7 9)))
+(assert-fail (map 'wrong + (vec 1 2 3)))
+(assert-fail (map (vec) + (vec 1 2 3)))
+(assert-fail (map (arr 'u8 1) + (vec 1 2 3)))
 
 ;; aref with multiple indices
 (def a #(#(0 1 2) #(3 (4 5 6) 7)))