: word, ( word -- )
[
word-tag >header ,
- dup hashcode ,
+ dup hashcode fixnum-tag immediate ,
0 ,
dup word-primitive ,
dup word-parameter ' ,
( elements -- ) [ emit ] each
align-here r> ;
-M: vector ' ( vector -- pointer )
+: emit-vector ( vector -- pointer )
dup vector>list emit-array swap vector-length
object-tag here-as >r
vector-type >header emit
emit ( array ptr )
align-here r> ;
+M: vector ' ( vector -- pointer )
+ emit-vector ;
+
+: rehash ( hashtable -- )
+ ! Now make a rehashing boot quotation
+ dup hash>alist [
+ >r dup vector-length [
+ f swap pick set-vector-nth
+ ] times* r>
+ [ unswons pick set-hash ] each
+ ] cons cons
+ boot-quot [ append ] change ;
+
+M: hashtable ' ( hashtable -- pointer )
+ #! Only hashtables are pooled, not vectors!
+ dup pooled-object dup [
+ nip
+ ] [
+ drop [ dup emit-vector [ pool-object ] keep ] keep
+ rehash
+ ] ifte ;
+
( End of the image )
: vocabularies, ( vocabularies -- )
global-offset fixup ;
: boot, ( quot -- )
- boot-quot get ' boot-quot-offset fixup ;
+ boot-quot get swap append ' boot-quot-offset fixup ;
-: end ( -- )
- boot,
+: end ( quot -- )
global,
+ boot,
fixup-words
here base - heap-size-offset fixup ;
] with-scope ;
: with-image ( quot -- image )
+ #! The quotation leaves a boot quotation on the stack.
[ begin call end ] with-minimal-image ;
: test-image ( quot -- ) with-image vector>list . ;
: make-image ( name -- )
#! Make an image for the C interpreter.
[
+ boot-quot off
"/library/bootstrap/boot.factor" run-resource
- boot-quot set
] with-image
swap write-image ;
: type-intersection ( list list -- list )
intersection [ > ] sort ;
+: lookup-union ( typelist -- class )
+ classes get hash [ object ] unless* ;
+
: class-or ( class class -- class )
#! Return a class that both classes are subclasses of.
swap builtin-supertypes
swap builtin-supertypes
- type-union classes get hash [ object ] unless* ;
+ type-union lookup-union ;
: class-and ( class class -- class )
#! Return a class that is a subclass of both, or raise an
over builtin-supertypes
over builtin-supertypes
type-intersection dup [
- nip nip classes get hash [ object ] unless*
+ nip nip lookup-union
] [
drop [
word-name , " and " , word-name ,
: terminator-quot? ( [ quot | type-prop ] -- ? )
car literal-value [ terminator? ] some? ;
-: dual-branch ( branchlist branch -- rstate )
+: dual-branch ( branch branchlist -- rstate )
#! Return a recursive state for a branch other than the
#! given one in the list.
- swap [ over eq? not ] subset nip car car value-recursion ;
+ [ over eq? not ] subset nip car car value-recursion ;
-SYMBOL: dual-recursive-state
-
-: recursive-branch ( branchlist value -- namespace )
- #! Return effect namespace if inference didn't fail.
+: recursive-branch ( branch branchlist -- )
[
- [ dual-branch dual-recursive-state set ] keep
- infer-branch
+ dupd dual-branch >r infer-branch r> set-base
] [
- [ 2drop f ] when
+ [ 2drop ] when
] catch ;
-: infer-base-cases ( branchlist -- list )
- dup [ dupd recursive-branch ] map [ ] subset nip ;
-
: infer-base-case ( branchlist -- )
- #! Can't do much if there is only one non-terminator branch.
- #! Either the word is not recursive, or it is recursive
- #! and the base case throws an error.
[
inferring-base-case on
- [ terminator-quot? not ] subset dup length 1 > [
- infer-base-cases unify-effects
- effect dual-recursive-state get set-base
- ] [
- drop
- ] ifte
-
- inferring-base-case off
+ dup [
+ 2dup terminator-quot? [
+ 2drop
+ ] [
+ recursive-branch
+ ] ifte
+ ] each drop
] with-scope ;
: (infer-branches) ( branchlist -- list )
: infer-quot ( quot -- )
#! Recursive calls to this word are made for nested
#! quotations.
- [
- [ apply-object ] each
- ] [
- [ swap <chained-error> rethrow ] when*
- ] catch ;
+ [ apply-object ] each ;
: raise ( [ in | out ] -- [ in | out ] )
uncons 2dup min tuck - >r - r> cons ;
#! Set the base case of the current word.
dup [
car cdr [
- entry-effect get swap decompose
+ [ effect ] bind entry-effect get swap decompose
base-case set
] bind
] [
: check-return ( -- )
#! Raise an error if word leaves values on return stack.
meta-r get vector-length 0 = [
- "Word leaves elements on return stack"
- <chained-error> throw
+ "Word leaves elements on return stack" throw
] unless ;
: values-node ( op -- )
: inline-compound ( word -- effect )
#! Infer the stack effect of a compound word in the current
#! inferencer instance.
- [
- gensym [ word-parameter infer-quot effect ] with-block
- ] [
- [ swap <chained-error> rethrow ] when*
- ] catch ;
+ gensym [ word-parameter infer-quot effect ] with-block ;
: infer-compound ( word -- effect )
#! Infer a word's stack effect in a separate inferencer
\ undefined-method t "terminator" set-word-property
\ not-a-number t "terminator" set-word-property
+\ throw t "terminator" set-word-property
[ fixnum* " x y -- x*y " [ [ fixnum fixnum ] [ integer ] ] ]
[ fixnum/i " x y -- x/y " [ [ fixnum fixnum ] [ integer ] ] ]
[ fixnum/f " x y -- x/y " [ [ fixnum fixnum ] [ integer ] ] ]
- [ fixnum-mod " x y -- x%y " [ [ fixnum fixnum ] [ integer ] ] ]
- [ fixnum/mod " x y -- x/y x%y " [ [ fixnum fixnum ] [ integer integer ] ] ]
+ [ fixnum-mod " x y -- x%y " [ [ fixnum fixnum ] [ fixnum ] ] ]
+ [ fixnum/mod " x y -- x/y x%y " [ [ fixnum fixnum ] [ integer fixnum ] ] ]
[ fixnum-bitand " x y -- x&y " [ [ fixnum fixnum ] [ fixnum ] ] ]
[ fixnum-bitor " x y -- x|y " [ [ fixnum fixnum ] [ fixnum ] ] ]
[ fixnum-bitxor " x y -- x^y " [ [ fixnum fixnum ] [ fixnum ] ] ]
[ [ "2 car" ] parse ] [ print-error ] catch
[ [ "\"\" { } vector-nth" ] parse ] [ type-check-error ] catch
-
-[ "cons" ] [ [ 1 2 ] type type-error-name ] unit-test
[ number ] [ object number class-and ] unit-test
[ t ] [ del1 builtin-supertypes [ integer? ] all? ] unit-test
+
+[ cons ] [ [ 1 2 ] class ] unit-test
"I/O error in kernel function " write
unswons write ": " write car print ;
-: type-error-name ( n -- string )
- #! These values are only used by the kernel for error
- #! reporting.
- dup [
- [ 100 | "fixnum/bignum" ]
- [ 104 | "fixnum/bignum/string" ]
- ] assoc dup [
- nip
- ] [
- drop type-name
- ] ifte ;
-
: type-check-error ( list -- )
"Type check error" print
uncons car dup "Object: " write .
- "Object type: " write type type-error-name print
- "Expected type: " write type-error-name print ;
+ "Object type: " write class .
+ "Expected type: " write type-name print ;
: range-error ( list -- )
"Range check error" print
M: string error. ( error -- )
print ;
-TRAITS: chained-error
-SYMBOL: original-error
-
-C: chained-error ( original chain -- )
- [ chained-error set original-error set ] extend ;
-
-M: chained-error error. ( error -- )
- [
- chained-error get error.
- " " [ original-error get error. ] with-prefix
- ] bind ;
-
M: object error. ( error -- )
. ;
dup 0 = [
3drop
] [
- rot type-name write ": " write
+ rot builtin-type word-name write ": " write
unparse write " bytes, " write
unparse write " instances" print
] ifte ;
BUILTIN: word 1
-M: word hashcode 1 integer-slot ;
+M: word hashcode 1 slot ;
: word-xt ( w -- xt ) >word 2 integer-slot ; inline
: set-word-xt ( xt w -- ) >word 2 set-integer-slot ; inline
case BIGNUM_TYPE:
return s48_bignum_to_long(untag_bignum(x));
default:
- type_error(INTEGER_TYPE,x);
+ type_error(BIGNUM_TYPE,x);
return 0;
}
}
else
return s48_bignum_to_long(untag_bignum(x));
default:
- type_error(INTEGER_TYPE,x);
+ type_error(BIGNUM_TYPE,x);
return 0;
}
}
gc_in_progress = true;
+ fprintf(stderr,"GC\n");
+ fflush(stderr);
+
flip_zones();
scan = active.here = active.base;
collect_roots();
sbuf_append_string(sbuf,untag_string(object));
break;
default:
- type_error(TEXT_TYPE,object);
+ type_error(STRING_TYPE,object);
break;
}
}
#define TYPE_COUNT 17
-/* Pseudo-types. For error reporting only. */
-#define INTEGER_TYPE 100 /* F_FIXNUM or BIGNUM */
-#define TEXT_TYPE 104 /* F_FIXNUM or F_STRING */
-
INLINE CELL tag_header(CELL cell)
{
return RETAG(cell << TAG_BITS,HEADER_TYPE);
write_string_8(port,str);
break;
default:
- type_error(TEXT_TYPE,text);
+ type_error(STRING_TYPE,text);
break;
}
}
write_string_8(port, untag_string(text));
break;
default:
- type_error(TEXT_TYPE, text);
+ type_error(STRING_TYPE, text);
break;
}
}
maybe_garbage_collection();
word = allot_object(WORD_TYPE,sizeof(F_WORD));
- word->hashcode = (CELL)word; /* initial address */
+ word->hashcode = tag_fixnum((CELL)word); /* initial address */
word->xt = (CELL)undefined;
word->primitive = 0;
word->parameter = F;