change _pointer to mean a reference to non-GCed memory; add _gcpointer (v4.2.2.6)
svn: r16546
This commit is contained in:
parent
4edc044cb6
commit
c49b22fa2c
|
@ -62,13 +62,13 @@
|
||||||
|
|
||||||
(provide* ctype-sizeof ctype-alignof compiler-sizeof
|
(provide* ctype-sizeof ctype-alignof compiler-sizeof
|
||||||
(unsafe malloc) (unsafe free) (unsafe end-stubborn-change)
|
(unsafe malloc) (unsafe free) (unsafe end-stubborn-change)
|
||||||
cpointer? ptr-equal? ptr-add (unsafe ptr-ref) (unsafe ptr-set!)
|
cpointer? ptr-equal? ptr-add (unsafe ptr-ref) (unsafe ptr-set!) (unsafe cast)
|
||||||
ptr-offset ptr-add! offset-ptr? set-ptr-offset!
|
ptr-offset ptr-add! offset-ptr? set-ptr-offset!
|
||||||
ctype? make-ctype make-cstruct-type (unsafe make-sized-byte-string) ctype->layout
|
ctype? make-ctype make-cstruct-type (unsafe make-sized-byte-string) ctype->layout
|
||||||
_void _int8 _uint8 _int16 _uint16 _int32 _uint32 _int64 _uint64
|
_void _int8 _uint8 _int16 _uint16 _int32 _uint32 _int64 _uint64
|
||||||
_fixint _ufixint _fixnum _ufixnum
|
_fixint _ufixint _fixnum _ufixnum
|
||||||
_float _double _double*
|
_float _double _double*
|
||||||
_bool _pointer _scheme _fpointer function-ptr
|
_bool _pointer _gcpointer _scheme _fpointer function-ptr
|
||||||
(unsafe memcpy) (unsafe memmove) (unsafe memset)
|
(unsafe memcpy) (unsafe memmove) (unsafe memset)
|
||||||
(unsafe malloc-immobile-cell) (unsafe free-immobile-cell))
|
(unsafe malloc-immobile-cell) (unsafe free-immobile-cell))
|
||||||
|
|
||||||
|
@ -1257,6 +1257,49 @@
|
||||||
;; Similar to the above, but can tolerate null pointers (#f).
|
;; Similar to the above, but can tolerate null pointers (#f).
|
||||||
(define* _cpointer/null (cpointer-maker #t))
|
(define* _cpointer/null (cpointer-maker #t))
|
||||||
|
|
||||||
|
(define (cast p from-type to-type)
|
||||||
|
(unless (ctype? from-type)
|
||||||
|
(raise-type-error 'cast "ctype" from-type))
|
||||||
|
(unless (ctype? to-type)
|
||||||
|
(raise-type-error 'cast "ctype" to-type))
|
||||||
|
(unless (= (ctype-sizeof to-type)
|
||||||
|
(ctype-sizeof from-type))
|
||||||
|
(raise-mismatch-error (format "representation sizes of types differ: ~e to "
|
||||||
|
from-type)
|
||||||
|
to-type))
|
||||||
|
(let ([p2 (malloc from-type)])
|
||||||
|
(ptr-set! p2 from-type p)
|
||||||
|
(ptr-ref p2 to-type)))
|
||||||
|
|
||||||
|
(define* (_or-null ctype)
|
||||||
|
(let ([coretype (ctype-coretype ctype)])
|
||||||
|
(unless (memq coretype '(pointer gcpointer fpointer))
|
||||||
|
(raise-type-error '_or-null "ctype buit on pointer, gcpointer, or fpointer" ctype))
|
||||||
|
(make-ctype
|
||||||
|
(case coretype
|
||||||
|
[(pointer) _pointer]
|
||||||
|
[(gcpointer) _gcpointer]
|
||||||
|
[(fpointer) _fpointer])
|
||||||
|
(lambda (v) (and v (cast _pointer v)))
|
||||||
|
(lambda (v) (and v (cast ctype v))))))
|
||||||
|
|
||||||
|
(define* (_gcable ctype)
|
||||||
|
(unless (memq (ctype-coretype ctype) '(pointer gcpointer))
|
||||||
|
(raise-type-error '_or-null "pointer ctype" ctype))
|
||||||
|
(let loop ([ctype ctype])
|
||||||
|
(if (eq? ctype 'pointer)
|
||||||
|
_gcpointer
|
||||||
|
(make-ctype
|
||||||
|
(loop (ctype-basetype ctype))
|
||||||
|
(ctype-scheme->c ctype)
|
||||||
|
(ctype-c->scheme ctype)))))
|
||||||
|
|
||||||
|
(define (ctype-coretype c)
|
||||||
|
(let loop ([c (ctype-basetype c)])
|
||||||
|
(if (symbol? c)
|
||||||
|
c
|
||||||
|
(loop c))))
|
||||||
|
|
||||||
;; A macro version of the above two functions, using the defined name for a tag
|
;; A macro version of the above two functions, using the defined name for a tag
|
||||||
;; string, and defining a predicate too. The name should look like `_foo', the
|
;; string, and defining a predicate too. The name should look like `_foo', the
|
||||||
;; predicate will be `foo?', and the tag will be "foo". In addition, `foo-tag'
|
;; predicate will be `foo?', and the tag will be "foo". In addition, `foo-tag'
|
||||||
|
|
|
@ -9,12 +9,12 @@ The unsafe @scheme[cpointer-has-tag?] and @scheme[cpointer-push-tag!]
|
||||||
operations manage tags to distinguish pointer types.
|
operations manage tags to distinguish pointer types.
|
||||||
|
|
||||||
@defproc*[([(_cpointer [tag any/c]
|
@defproc*[([(_cpointer [tag any/c]
|
||||||
[ptr-type ctype? _pointer]
|
[ptr-type ctype? _xpointer]
|
||||||
[scheme-to-c (any/c . -> . any/c) values]
|
[scheme-to-c (any/c . -> . any/c) values]
|
||||||
[c-to-scheme (any/c . -> . any/c) values])
|
[c-to-scheme (any/c . -> . any/c) values])
|
||||||
ctype]
|
ctype]
|
||||||
[(_cpointer/null [tag any/c]
|
[(_cpointer/null [tag any/c]
|
||||||
[ptr-type ctype? _pointer]
|
[ptr-type ctype? _xpointer]
|
||||||
[scheme-to-c (any/c . -> . any/c) values]
|
[scheme-to-c (any/c . -> . any/c) values]
|
||||||
[c-to-scheme (any/c . -> . any/c) values])
|
[c-to-scheme (any/c . -> . any/c) values])
|
||||||
ctype])]{
|
ctype])]{
|
||||||
|
|
|
@ -54,6 +54,20 @@ Like @scheme[list->cblock], but for Scheme vectors.}
|
||||||
|
|
||||||
@section{Unsafe Miscellaneous Operations}
|
@section{Unsafe Miscellaneous Operations}
|
||||||
|
|
||||||
|
@defproc[(cast [v any/c][from-type ctype?][to-type ctype?]) any/c]{
|
||||||
|
|
||||||
|
Converts @scheme[v] from a value matching @scheme[from-type] to a
|
||||||
|
value matching @scheme[to-type], where @scheme[(ctype-size from-type)]
|
||||||
|
matches @scheme[(ctype-size to-type)].
|
||||||
|
|
||||||
|
The conversion is equivalent to
|
||||||
|
|
||||||
|
@schemeblock[
|
||||||
|
(let ([p (malloc from-type)])
|
||||||
|
(ptr-set! p from-type v)
|
||||||
|
(ptr-ref p to-type))
|
||||||
|
]}
|
||||||
|
|
||||||
@defproc[(cblock->list [cblock any/c][type ctype?][length exact-nonnegative-integer?])
|
@defproc[(cblock->list [cblock any/c][type ctype?][length exact-nonnegative-integer?])
|
||||||
list?]{
|
list?]{
|
||||||
|
|
||||||
|
|
|
@ -260,8 +260,8 @@ specification is required at minimum:
|
||||||
]
|
]
|
||||||
|
|
||||||
If no mode is specified, then @scheme['nonatomic] allocation is used
|
If no mode is specified, then @scheme['nonatomic] allocation is used
|
||||||
when the type is any pointer-based type, and @scheme['atomic]
|
when the type is a @scheme[_gcpointer]- or @scheme[_scheme]-based
|
||||||
allocation is used otherwise.}
|
type, and @scheme['atomic] allocation is used otherwise.}
|
||||||
|
|
||||||
|
|
||||||
@defproc[(free [cptr cpointer?]) void]{
|
@defproc[(free [cptr cpointer?]) void]{
|
||||||
|
|
|
@ -271,7 +271,28 @@ Corresponds to Scheme ``C pointer'' objects. These pointers can have
|
||||||
an arbitrary Scheme object attached as a type tag. The tag is ignored
|
an arbitrary Scheme object attached as a type tag. The tag is ignored
|
||||||
by built-in functionality; it is intended to be used by interfaces.
|
by built-in functionality; it is intended to be used by interfaces.
|
||||||
See @secref["foreign:tagged-pointers"] for creating pointer types that
|
See @secref["foreign:tagged-pointers"] for creating pointer types that
|
||||||
use these tags for safety.}
|
use these tags for safety. A @scheme[#f] value is converted to
|
||||||
|
@cpp{NULL} and vice-versa.
|
||||||
|
|
||||||
|
The address referenced by a @scheme[_pointer] value must not refer to
|
||||||
|
memory managed by the garbage collector (unless the address
|
||||||
|
corresponds to a value that supports interior pointers and that is
|
||||||
|
otherwise referenced to preserve the value from garbage collection).
|
||||||
|
The reference is not traced or updated by the garbage collector.}
|
||||||
|
|
||||||
|
|
||||||
|
@defthing[_gcpointer ctype?]{
|
||||||
|
|
||||||
|
Like @scheme[_pointer], but for a value that can refer to memory
|
||||||
|
managed by the garbage collector.
|
||||||
|
|
||||||
|
Although a @scheme[_gcpointer] can reference to memory that is not
|
||||||
|
managed by the garbage collector, beware of using an address that
|
||||||
|
might eventually become managed by the garbage collector. For example,
|
||||||
|
if a reference is created by @scheme[malloc] with @scheme['raw] and
|
||||||
|
released by @scheme[free], then the @scheme[free] may allow the memory
|
||||||
|
formerly occupied by the reference to be used later by the garbage
|
||||||
|
collector.}
|
||||||
|
|
||||||
|
|
||||||
@defthing[_scheme ctype?]{
|
@defthing[_scheme ctype?]{
|
||||||
|
@ -295,6 +316,24 @@ A type generated by @scheme[_cprocedure] builds on @scheme[_fpointer],
|
||||||
and normally @scheme[_cprocedure] should be used instead of
|
and normally @scheme[_cprocedure] should be used instead of
|
||||||
@scheme[_fpointer].}
|
@scheme[_fpointer].}
|
||||||
|
|
||||||
|
|
||||||
|
@defproc[(_or-null [ctype ctype?]) ctype?]{
|
||||||
|
|
||||||
|
Creates a type that is like @scheme[ctype], but @scheme[#f] is
|
||||||
|
converted to @cpp{NULL} and vice-versa. The given @scheme[ctype] must
|
||||||
|
have the same C representation as @scheme[_pointer],
|
||||||
|
@scheme[_gcpointer], or @scheme[_fpointer].}
|
||||||
|
|
||||||
|
|
||||||
|
@defproc[(_gcable [ctype ctype?]) ctype?]{
|
||||||
|
|
||||||
|
Creates a type that is like @scheme[ctype], but whose base
|
||||||
|
representation is like @scheme[_gcpointer] instead of
|
||||||
|
@scheme[_pointer]. The given @scheme[ctype] must have a base
|
||||||
|
representation like @scheme[_pointer] or @scheme[_gcpointer] (and in
|
||||||
|
the later case, the result is the @scheme[ctype]).}
|
||||||
|
|
||||||
|
|
||||||
@; ------------------------------------------------------------
|
@; ------------------------------------------------------------
|
||||||
|
|
||||||
@section[#:tag "foreign:procedures"]{Function Types}
|
@section[#:tag "foreign:procedures"]{Function Types}
|
||||||
|
|
|
@ -667,7 +667,21 @@ Creates a C-pointer object that encapsulates @var{ptr} and uses
|
||||||
the original @var{ptr} from the Scheme object, and
|
the original @var{ptr} from the Scheme object, and
|
||||||
@cppi{SCHEME_CPTR_TYPE} extracts the type tag.
|
@cppi{SCHEME_CPTR_TYPE} extracts the type tag.
|
||||||
The @cppi{SCHEME_CPTR_OFFSETVAL} macro returns @cpp{0}
|
The @cppi{SCHEME_CPTR_OFFSETVAL} macro returns @cpp{0}
|
||||||
for the result Scheme object.}
|
for the result Scheme object.
|
||||||
|
|
||||||
|
The @var{ptr} can refer to either memory managed by the garbage
|
||||||
|
collector or by some other memory manager. Beware, however, of
|
||||||
|
retaining a @var{ptr} that refers to memory released by another
|
||||||
|
memory manager, since the enclosing memory range might later become
|
||||||
|
managed by the garbage collector (in which case @var{ptr} might
|
||||||
|
become an invalid pointer that can crash the garbage collector).}
|
||||||
|
|
||||||
|
@function[(Scheme_Object* scheme_make_external_cptr
|
||||||
|
[void* ptr]
|
||||||
|
[const-Scheme_Object* typetag])]{
|
||||||
|
|
||||||
|
Like @cpp{scheme_make_cptr}, but @var{ptr} is never treated as
|
||||||
|
referencing memory managed by the garbage collector.}
|
||||||
|
|
||||||
@function[(Scheme_Object* scheme_make_offset_cptr
|
@function[(Scheme_Object* scheme_make_offset_cptr
|
||||||
[void* ptr]
|
[void* ptr]
|
||||||
|
@ -677,7 +691,20 @@ Creates a C-pointer object that encapsulates @var{ptr} and uses
|
||||||
Creates a C-pointer object that encapsulates both @var{ptr} and @var{offset}.
|
Creates a C-pointer object that encapsulates both @var{ptr} and @var{offset}.
|
||||||
The @cppi{SCHEME_CPTR_OFFSETVAL} macro returns @var{offset}
|
The @cppi{SCHEME_CPTR_OFFSETVAL} macro returns @var{offset}
|
||||||
for the result Scheme object (and the macro be used to change the offset,
|
for the result Scheme object (and the macro be used to change the offset,
|
||||||
since it also works on objects with no offset).}
|
since it also works on objects with no offset).
|
||||||
|
|
||||||
|
The @var{ptr} can refer to either memory managed by the garbage
|
||||||
|
collector or by some other memory manager; see also
|
||||||
|
@cpp{scheme_make_cptr}.}
|
||||||
|
|
||||||
|
@function[(Scheme_Object* scheme_make_offset_external_cptr
|
||||||
|
[void* ptr]
|
||||||
|
[long offset]
|
||||||
|
[const-Scheme_Object* typetag])]{
|
||||||
|
|
||||||
|
Like @cpp{scheme_make_offset_cptr}, but @var{ptr} is never treated as
|
||||||
|
referencing memory managed by the garbage collector.}
|
||||||
|
|
||||||
|
|
||||||
@function[(void scheme_set_type_printer
|
@function[(void scheme_set_type_printer
|
||||||
[Scheme_Type type]
|
[Scheme_Type type]
|
||||||
|
|
|
@ -766,14 +766,24 @@ Scheme_Object *utf16_pointer_to_ucs4_string(unsigned short *utf)
|
||||||
* Predicate: SCHEME_FFIANYPTRP(<Scheme>)
|
* Predicate: SCHEME_FFIANYPTRP(<Scheme>)
|
||||||
* Scheme->C: SCHEME_FFIANYPTR_VAL(<Scheme>)
|
* Scheme->C: SCHEME_FFIANYPTR_VAL(<Scheme>)
|
||||||
* S->C offset: FFIANYPTR
|
* S->C offset: FFIANYPTR
|
||||||
|
* C->Scheme: scheme_make_foreign_external_cpointer(<C>)
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define FOREIGN_gcpointer (24)
|
||||||
|
/* Type Name: gcpointer
|
||||||
|
* LibFfi type: ffi_type_gcpointer
|
||||||
|
* C type: void*
|
||||||
|
* Predicate: SCHEME_FFIANYPTRP(<Scheme>)
|
||||||
|
* Scheme->C: SCHEME_FFIANYPTR_VAL(<Scheme>)
|
||||||
|
* S->C offset: FFIANYPTR
|
||||||
* C->Scheme: scheme_make_foreign_cpointer(<C>)
|
* C->Scheme: scheme_make_foreign_cpointer(<C>)
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* This is used for passing and Scheme_Object* value as is. Useful for
|
/* This is used for passing and Scheme_Object* value as is. Useful for
|
||||||
* functions that know about Scheme_Object*s, like MzScheme's. */
|
* functions that know about Scheme_Object*s, like MzScheme's. */
|
||||||
#define FOREIGN_scheme (24)
|
#define FOREIGN_scheme (25)
|
||||||
/* Type Name: scheme
|
/* Type Name: scheme
|
||||||
* LibFfi type: ffi_type_pointer
|
* LibFfi type: ffi_type_gcpointer
|
||||||
* C type: Scheme_Object*
|
* C type: Scheme_Object*
|
||||||
* Predicate: 1
|
* Predicate: 1
|
||||||
* Scheme->C: <Scheme>
|
* Scheme->C: <Scheme>
|
||||||
|
@ -784,7 +794,7 @@ Scheme_Object *utf16_pointer_to_ucs4_string(unsigned short *utf)
|
||||||
/* Special type, not actually used for anything except to mark values
|
/* Special type, not actually used for anything except to mark values
|
||||||
* that are treated like pointers but not referenced. Used for
|
* that are treated like pointers but not referenced. Used for
|
||||||
* creating function types. */
|
* creating function types. */
|
||||||
#define FOREIGN_fpointer (25)
|
#define FOREIGN_fpointer (26)
|
||||||
/* Type Name: fpointer
|
/* Type Name: fpointer
|
||||||
* LibFfi type: ffi_type_pointer
|
* LibFfi type: ffi_type_pointer
|
||||||
* C type: void*
|
* C type: void*
|
||||||
|
@ -817,12 +827,13 @@ typedef union _ForeignAny {
|
||||||
char* x_path;
|
char* x_path;
|
||||||
char* x_symbol;
|
char* x_symbol;
|
||||||
void* x_pointer;
|
void* x_pointer;
|
||||||
|
void* x_gcpointer;
|
||||||
Scheme_Object* x_scheme;
|
Scheme_Object* x_scheme;
|
||||||
void* x_fpointer;
|
void* x_fpointer;
|
||||||
} ForeignAny;
|
} ForeignAny;
|
||||||
|
|
||||||
/* This is a tag that is used to identify user-made struct types. */
|
/* This is a tag that is used to identify user-made struct types. */
|
||||||
#define FOREIGN_struct (26)
|
#define FOREIGN_struct (27)
|
||||||
|
|
||||||
/*****************************************************************************/
|
/*****************************************************************************/
|
||||||
/* Type objects */
|
/* Type objects */
|
||||||
|
@ -876,6 +887,8 @@ int ctype_FIXUP(void *p) {
|
||||||
END_XFORM_SKIP;
|
END_XFORM_SKIP;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
static ffi_type ffi_type_gcpointer;
|
||||||
|
|
||||||
#define CTYPE_BASETYPE(x) (((ctype_struct*)(x))->basetype)
|
#define CTYPE_BASETYPE(x) (((ctype_struct*)(x))->basetype)
|
||||||
#define CTYPE_USERP(x) (CTYPE_BASETYPE(x) != NULL && SCHEME_CTYPEP(CTYPE_BASETYPE(x)))
|
#define CTYPE_USERP(x) (CTYPE_BASETYPE(x) != NULL && SCHEME_CTYPEP(CTYPE_BASETYPE(x)))
|
||||||
#define CTYPE_PRIMP(x) (!CTYPE_USERP(x))
|
#define CTYPE_PRIMP(x) (!CTYPE_USERP(x))
|
||||||
|
@ -951,6 +964,7 @@ static int ctype_sizeof(Scheme_Object *type)
|
||||||
case FOREIGN_path: return sizeof(char*);
|
case FOREIGN_path: return sizeof(char*);
|
||||||
case FOREIGN_symbol: return sizeof(char*);
|
case FOREIGN_symbol: return sizeof(char*);
|
||||||
case FOREIGN_pointer: return sizeof(void*);
|
case FOREIGN_pointer: return sizeof(void*);
|
||||||
|
case FOREIGN_gcpointer: return sizeof(void*);
|
||||||
case FOREIGN_scheme: return sizeof(Scheme_Object*);
|
case FOREIGN_scheme: return sizeof(Scheme_Object*);
|
||||||
case FOREIGN_fpointer: return sizeof(void*);
|
case FOREIGN_fpointer: return sizeof(void*);
|
||||||
/* for structs */
|
/* for structs */
|
||||||
|
@ -1148,6 +1162,9 @@ END_XFORM_SKIP;
|
||||||
#define scheme_make_foreign_cpointer(x) \
|
#define scheme_make_foreign_cpointer(x) \
|
||||||
((x==NULL)?scheme_false:scheme_make_cptr(x,NULL))
|
((x==NULL)?scheme_false:scheme_make_cptr(x,NULL))
|
||||||
|
|
||||||
|
#define scheme_make_foreign_external_cpointer(x) \
|
||||||
|
((x==NULL)?scheme_false:scheme_make_external_cptr(x,NULL))
|
||||||
|
|
||||||
#define MYNAME "cpointer?"
|
#define MYNAME "cpointer?"
|
||||||
static Scheme_Object *foreign_cpointer_p(int argc, Scheme_Object *argv[])
|
static Scheme_Object *foreign_cpointer_p(int argc, Scheme_Object *argv[])
|
||||||
{
|
{
|
||||||
|
@ -1206,7 +1223,7 @@ static Scheme_Object *C2SCHEME(Scheme_Object *type, void *src,
|
||||||
else
|
else
|
||||||
return _scheme_apply(CTYPE_USER_C2S(type), 1, (Scheme_Object**)(&res));
|
return _scheme_apply(CTYPE_USER_C2S(type), 1, (Scheme_Object**)(&res));
|
||||||
} else if (CTYPE_PRIMLABEL(type) == FOREIGN_fpointer) {
|
} else if (CTYPE_PRIMLABEL(type) == FOREIGN_fpointer) {
|
||||||
return scheme_make_foreign_cpointer(*(void **)W_OFFSET(src, delta));
|
return scheme_make_foreign_external_cpointer(*(void **)W_OFFSET(src, delta));
|
||||||
} else switch (CTYPE_PRIMLABEL(type)) {
|
} else switch (CTYPE_PRIMLABEL(type)) {
|
||||||
case FOREIGN_void: return scheme_void;
|
case FOREIGN_void: return scheme_void;
|
||||||
case FOREIGN_int8: return scheme_make_integer(REF_CTYPE(Tsint8));
|
case FOREIGN_int8: return scheme_make_integer(REF_CTYPE(Tsint8));
|
||||||
|
@ -1230,7 +1247,8 @@ static Scheme_Object *C2SCHEME(Scheme_Object *type, void *src,
|
||||||
case FOREIGN_bytes: return (REF_CTYPE(char*)==NULL)?scheme_false:scheme_make_byte_string_without_copying(REF_CTYPE(char*));
|
case FOREIGN_bytes: return (REF_CTYPE(char*)==NULL)?scheme_false:scheme_make_byte_string_without_copying(REF_CTYPE(char*));
|
||||||
case FOREIGN_path: return (REF_CTYPE(char*)==NULL)?scheme_false:scheme_make_path_without_copying(REF_CTYPE(char*));
|
case FOREIGN_path: return (REF_CTYPE(char*)==NULL)?scheme_false:scheme_make_path_without_copying(REF_CTYPE(char*));
|
||||||
case FOREIGN_symbol: return scheme_intern_symbol(REF_CTYPE(char*));
|
case FOREIGN_symbol: return scheme_intern_symbol(REF_CTYPE(char*));
|
||||||
case FOREIGN_pointer: return scheme_make_foreign_cpointer(REF_CTYPE(void*));
|
case FOREIGN_pointer: return scheme_make_foreign_external_cpointer(REF_CTYPE(void*));
|
||||||
|
case FOREIGN_gcpointer: return scheme_make_foreign_cpointer(REF_CTYPE(void*));
|
||||||
case FOREIGN_scheme: return REF_CTYPE(Scheme_Object*);
|
case FOREIGN_scheme: return REF_CTYPE(Scheme_Object*);
|
||||||
case FOREIGN_fpointer: return (REF_CTYPE(void*));
|
case FOREIGN_fpointer: return (REF_CTYPE(void*));
|
||||||
case FOREIGN_struct:
|
case FOREIGN_struct:
|
||||||
|
@ -1599,6 +1617,23 @@ static void* SCHEME2C(Scheme_Object *type, void *dst, long delta,
|
||||||
scheme_wrong_type("Scheme->C","pointer",0,1,&(val));
|
scheme_wrong_type("Scheme->C","pointer",0,1,&(val));
|
||||||
return NULL; /* hush the compiler */
|
return NULL; /* hush the compiler */
|
||||||
}
|
}
|
||||||
|
case FOREIGN_gcpointer:
|
||||||
|
# ifdef SCHEME_BIG_ENDIAN
|
||||||
|
if (sizeof(void*)<sizeof(int) && ret_loc) {
|
||||||
|
((int*)W_OFFSET(dst,delta))[0] = 0;
|
||||||
|
delta += (sizeof(int)-sizeof(void*));
|
||||||
|
}
|
||||||
|
# endif /* SCHEME_BIG_ENDIAN */
|
||||||
|
if (SCHEME_FFIANYPTRP(val)) {
|
||||||
|
void* tmp; long toff;
|
||||||
|
tmp = (void*)(SCHEME_FFIANYPTR_VAL(val));
|
||||||
|
toff = SCHEME_FFIANYPTR_OFFSET(val);
|
||||||
|
if (_offset) *_offset = toff;
|
||||||
|
(((void**)W_OFFSET(dst,delta))[0]) = tmp; return NULL;
|
||||||
|
} else {
|
||||||
|
scheme_wrong_type("Scheme->C","gcpointer",0,1,&(val));
|
||||||
|
return NULL; /* hush the compiler */
|
||||||
|
}
|
||||||
case FOREIGN_scheme:
|
case FOREIGN_scheme:
|
||||||
# ifdef SCHEME_BIG_ENDIAN
|
# ifdef SCHEME_BIG_ENDIAN
|
||||||
if (sizeof(Scheme_Object*)<sizeof(int) && ret_loc) {
|
if (sizeof(Scheme_Object*)<sizeof(int) && ret_loc) {
|
||||||
|
@ -1609,13 +1644,7 @@ static void* SCHEME2C(Scheme_Object *type, void *dst, long delta,
|
||||||
if (1) {
|
if (1) {
|
||||||
Scheme_Object* tmp;
|
Scheme_Object* tmp;
|
||||||
tmp = (Scheme_Object*)(val);
|
tmp = (Scheme_Object*)(val);
|
||||||
if (basetype_p == NULL || tmp == NULL) {
|
(((Scheme_Object**)W_OFFSET(dst,delta))[0]) = tmp; return NULL;
|
||||||
(((Scheme_Object**)W_OFFSET(dst,delta))[0]) = tmp;
|
|
||||||
return NULL;
|
|
||||||
} else {
|
|
||||||
*basetype_p = FOREIGN_scheme;
|
|
||||||
return tmp;
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
scheme_wrong_type("Scheme->C","scheme",0,1,&(val));
|
scheme_wrong_type("Scheme->C","scheme",0,1,&(val));
|
||||||
return NULL; /* hush the compiler */
|
return NULL; /* hush the compiler */
|
||||||
|
@ -1845,7 +1874,7 @@ static Scheme_Object *foreign_malloc(int argc, Scheme_Object *argv[])
|
||||||
if ((num == 0) && (size == 0)) scheme_signal_error(MYNAME": no size given");
|
if ((num == 0) && (size == 0)) scheme_signal_error(MYNAME": no size given");
|
||||||
size = ((size==0) ? 1 : size) * ((num==0) ? 1 : num);
|
size = ((size==0) ? 1 : size) * ((num==0) ? 1 : num);
|
||||||
if (mode == NULL)
|
if (mode == NULL)
|
||||||
mf = (base != NULL && CTYPE_PRIMTYPE(base) == &ffi_type_pointer)
|
mf = (base != NULL && CTYPE_PRIMTYPE(base) == &ffi_type_gcpointer)
|
||||||
? scheme_malloc : scheme_malloc_atomic;
|
? scheme_malloc : scheme_malloc_atomic;
|
||||||
else if (SAME_OBJ(mode, nonatomic_sym)) mf = scheme_malloc;
|
else if (SAME_OBJ(mode, nonatomic_sym)) mf = scheme_malloc;
|
||||||
else if (SAME_OBJ(mode, atomic_sym)) mf = scheme_malloc_atomic;
|
else if (SAME_OBJ(mode, atomic_sym)) mf = scheme_malloc_atomic;
|
||||||
|
@ -1862,7 +1891,10 @@ static Scheme_Object *foreign_malloc(int argc, Scheme_Object *argv[])
|
||||||
if (failok) res = scheme_malloc_fail_ok(mf,size); else res = mf(size);
|
if (failok) res = scheme_malloc_fail_ok(mf,size); else res = mf(size);
|
||||||
if (((from != NULL) || (foff != 0)) && (res != NULL))
|
if (((from != NULL) || (foff != 0)) && (res != NULL))
|
||||||
memcpy(res, W_OFFSET(from, foff), size);
|
memcpy(res, W_OFFSET(from, foff), size);
|
||||||
return scheme_make_foreign_cpointer(res);
|
if (SAME_OBJ(mode, raw_sym))
|
||||||
|
return scheme_make_foreign_external_cpointer(res);
|
||||||
|
else
|
||||||
|
return scheme_make_foreign_cpointer(res);
|
||||||
}
|
}
|
||||||
#undef MYNAME
|
#undef MYNAME
|
||||||
|
|
||||||
|
@ -1906,7 +1938,7 @@ static Scheme_Object *foreign_free(int argc, Scheme_Object *argv[])
|
||||||
#define MYNAME "malloc-immobile-cell"
|
#define MYNAME "malloc-immobile-cell"
|
||||||
static Scheme_Object *foreign_malloc_immobile_cell(int argc, Scheme_Object *argv[])
|
static Scheme_Object *foreign_malloc_immobile_cell(int argc, Scheme_Object *argv[])
|
||||||
{
|
{
|
||||||
return scheme_make_foreign_cpointer(scheme_malloc_immobile_box(argv[0]));
|
return scheme_make_foreign_external_cpointer(scheme_malloc_immobile_box(argv[0]));
|
||||||
}
|
}
|
||||||
#undef MYNAME
|
#undef MYNAME
|
||||||
|
|
||||||
|
@ -1961,10 +1993,16 @@ static Scheme_Object *do_ptr_add(const char *who, int is_bang,
|
||||||
((Scheme_Offset_Cptr*)(argv[0]))->offset += noff;
|
((Scheme_Offset_Cptr*)(argv[0]))->offset += noff;
|
||||||
return scheme_void;
|
return scheme_void;
|
||||||
} else {
|
} else {
|
||||||
return scheme_make_offset_cptr
|
if (SCHEME_CPTRP(argv[0]) && (SCHEME_CPTR_FLAGS(argv[0]) & 0x1))
|
||||||
(SCHEME_FFIANYPTR_VAL(argv[0]),
|
return scheme_make_offset_external_cptr
|
||||||
SCHEME_FFIANYPTR_OFFSET(argv[0]) + noff,
|
(SCHEME_FFIANYPTR_VAL(argv[0]),
|
||||||
(SCHEME_CPTRP(argv[0])) ? SCHEME_CPTR_TYPE(argv[0]) : NULL);
|
SCHEME_FFIANYPTR_OFFSET(argv[0]) + noff,
|
||||||
|
(SCHEME_CPTRP(argv[0])) ? SCHEME_CPTR_TYPE(argv[0]) : NULL);
|
||||||
|
else
|
||||||
|
return scheme_make_offset_cptr
|
||||||
|
(SCHEME_FFIANYPTR_VAL(argv[0]),
|
||||||
|
SCHEME_FFIANYPTR_OFFSET(argv[0]) + noff,
|
||||||
|
(SCHEME_CPTRP(argv[0])) ? SCHEME_CPTR_TYPE(argv[0]) : NULL);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2741,6 +2779,7 @@ void scheme_init_foreign(Scheme_Env *env)
|
||||||
Scheme_Env *menv;
|
Scheme_Env *menv;
|
||||||
ctype_struct *t;
|
ctype_struct *t;
|
||||||
Scheme_Object *s;
|
Scheme_Object *s;
|
||||||
|
memcpy(&ffi_type_gcpointer, &ffi_type_pointer, sizeof(ffi_type_pointer));
|
||||||
menv = scheme_primitive_module(scheme_intern_symbol("#%foreign"), env);
|
menv = scheme_primitive_module(scheme_intern_symbol("#%foreign"), env);
|
||||||
scheme_add_global("ffi-lib?",
|
scheme_add_global("ffi-lib?",
|
||||||
scheme_make_prim_w_arity(foreign_ffi_lib_p, "ffi-lib?", 1, 1), menv);
|
scheme_make_prim_w_arity(foreign_ffi_lib_p, "ffi-lib?", 1, 1), menv);
|
||||||
|
@ -2981,11 +3020,18 @@ void scheme_init_foreign(Scheme_Env *env)
|
||||||
t->scheme_to_c = ((Scheme_Object*)(void*)(&ffi_type_pointer));
|
t->scheme_to_c = ((Scheme_Object*)(void*)(&ffi_type_pointer));
|
||||||
t->c_to_scheme = ((Scheme_Object*)FOREIGN_pointer);
|
t->c_to_scheme = ((Scheme_Object*)FOREIGN_pointer);
|
||||||
scheme_add_global("_pointer", (Scheme_Object*)t, menv);
|
scheme_add_global("_pointer", (Scheme_Object*)t, menv);
|
||||||
|
s = scheme_intern_symbol("gcpointer");
|
||||||
|
t = (ctype_struct*)scheme_malloc_tagged(sizeof(ctype_struct));
|
||||||
|
t->so.type = ctype_tag;
|
||||||
|
t->basetype = (s);
|
||||||
|
t->scheme_to_c = ((Scheme_Object*)(void*)(&ffi_type_gcpointer));
|
||||||
|
t->c_to_scheme = ((Scheme_Object*)FOREIGN_gcpointer);
|
||||||
|
scheme_add_global("_gcpointer", (Scheme_Object*)t, menv);
|
||||||
s = scheme_intern_symbol("scheme");
|
s = scheme_intern_symbol("scheme");
|
||||||
t = (ctype_struct*)scheme_malloc_tagged(sizeof(ctype_struct));
|
t = (ctype_struct*)scheme_malloc_tagged(sizeof(ctype_struct));
|
||||||
t->so.type = ctype_tag;
|
t->so.type = ctype_tag;
|
||||||
t->basetype = (s);
|
t->basetype = (s);
|
||||||
t->scheme_to_c = ((Scheme_Object*)(void*)(&ffi_type_pointer));
|
t->scheme_to_c = ((Scheme_Object*)(void*)(&ffi_type_gcpointer));
|
||||||
t->c_to_scheme = ((Scheme_Object*)FOREIGN_scheme);
|
t->c_to_scheme = ((Scheme_Object*)FOREIGN_scheme);
|
||||||
scheme_add_global("_scheme", (Scheme_Object*)t, menv);
|
scheme_add_global("_scheme", (Scheme_Object*)t, menv);
|
||||||
s = scheme_intern_symbol("fpointer");
|
s = scheme_intern_symbol("fpointer");
|
||||||
|
|
|
@ -704,6 +704,13 @@ Scheme_Object *utf16_pointer_to_ucs4_string(unsigned short *utf)
|
||||||
* ffi-obj and string values pass their pointer. When used as a return
|
* ffi-obj and string values pass their pointer. When used as a return
|
||||||
* value, either a cpointer object or #f is returned. */
|
* value, either a cpointer object or #f is returned. */
|
||||||
@(defctype 'pointer
|
@(defctype 'pointer
|
||||||
|
'ctype "void*"
|
||||||
|
'macro "FFIANYPTR"
|
||||||
|
'offset "FFIANYPTR"
|
||||||
|
'c->s "scheme_make_foreign_external_cpointer")
|
||||||
|
|
||||||
|
@(defctype 'gcpointer
|
||||||
|
'ftype "gcpointer"
|
||||||
'ctype "void*"
|
'ctype "void*"
|
||||||
'macro "FFIANYPTR"
|
'macro "FFIANYPTR"
|
||||||
'offset "FFIANYPTR"
|
'offset "FFIANYPTR"
|
||||||
|
@ -721,7 +728,7 @@ Scheme_Object *utf16_pointer_to_ucs4_string(unsigned short *utf)
|
||||||
/* This is used for passing and Scheme_Object* value as is. Useful for
|
/* This is used for passing and Scheme_Object* value as is. Useful for
|
||||||
* functions that know about Scheme_Object*s, like MzScheme's. */
|
* functions that know about Scheme_Object*s, like MzScheme's. */
|
||||||
@(defctype 'scheme
|
@(defctype 'scheme
|
||||||
'ftype "pointer"
|
'ftype "gcpointer"
|
||||||
'ctype "Scheme_Object*"
|
'ctype "Scheme_Object*"
|
||||||
'pred (lambda (x aux) "1")
|
'pred (lambda (x aux) "1")
|
||||||
's->c (lambda (x aux) x)
|
's->c (lambda (x aux) x)
|
||||||
|
@ -759,6 +766,8 @@ typedef union _ForeignAny {
|
||||||
[scheme_to_c "Scheme_Object*"]
|
[scheme_to_c "Scheme_Object*"]
|
||||||
[c_to_scheme "Scheme_Object*"]]
|
[c_to_scheme "Scheme_Object*"]]
|
||||||
|
|
||||||
|
static ffi_type ffi_type_gcpointer;
|
||||||
|
|
||||||
#define CTYPE_BASETYPE(x) (((ctype_struct*)(x))->basetype)
|
#define CTYPE_BASETYPE(x) (((ctype_struct*)(x))->basetype)
|
||||||
#define CTYPE_USERP(x) (CTYPE_BASETYPE(x) != NULL && SCHEME_CTYPEP(CTYPE_BASETYPE(x)))
|
#define CTYPE_USERP(x) (CTYPE_BASETYPE(x) != NULL && SCHEME_CTYPEP(CTYPE_BASETYPE(x)))
|
||||||
#define CTYPE_PRIMP(x) (!CTYPE_USERP(x))
|
#define CTYPE_PRIMP(x) (!CTYPE_USERP(x))
|
||||||
|
@ -950,6 +959,9 @@ ffi_abi sym_to_abi(char *who, Scheme_Object *sym)
|
||||||
#define scheme_make_foreign_cpointer(x) \
|
#define scheme_make_foreign_cpointer(x) \
|
||||||
((x==NULL)?scheme_false:scheme_make_cptr(x,NULL))
|
((x==NULL)?scheme_false:scheme_make_cptr(x,NULL))
|
||||||
|
|
||||||
|
#define scheme_make_foreign_external_cpointer(x) \
|
||||||
|
((x==NULL)?scheme_false:scheme_make_external_cptr(x,NULL))
|
||||||
|
|
||||||
@cdefine[cpointer? 1]{
|
@cdefine[cpointer? 1]{
|
||||||
return SCHEME_FFIANYPTRP(argv[0]) ? scheme_true : scheme_false;
|
return SCHEME_FFIANYPTRP(argv[0]) ? scheme_true : scheme_false;
|
||||||
}
|
}
|
||||||
|
@ -999,7 +1011,7 @@ static Scheme_Object *C2SCHEME(Scheme_Object *type, void *src,
|
||||||
else
|
else
|
||||||
return _scheme_apply(CTYPE_USER_C2S(type), 1, (Scheme_Object**)(&res));
|
return _scheme_apply(CTYPE_USER_C2S(type), 1, (Scheme_Object**)(&res));
|
||||||
} else if (CTYPE_PRIMLABEL(type) == FOREIGN_fpointer) {
|
} else if (CTYPE_PRIMLABEL(type) == FOREIGN_fpointer) {
|
||||||
return scheme_make_foreign_cpointer(*(void **)W_OFFSET(src, delta));
|
return scheme_make_foreign_external_cpointer(*(void **)W_OFFSET(src, delta));
|
||||||
} else switch (CTYPE_PRIMLABEL(type)) {
|
} else switch (CTYPE_PRIMLABEL(type)) {
|
||||||
@(map-types
|
@(map-types
|
||||||
@list{case FOREIGN_@|cname|: return @;
|
@list{case FOREIGN_@|cname|: return @;
|
||||||
|
@ -1307,7 +1319,7 @@ static void* SCHEME2C(Scheme_Object *type, void *dst, long delta,
|
||||||
if ((num == 0) && (size == 0)) scheme_signal_error(MYNAME": no size given");
|
if ((num == 0) && (size == 0)) scheme_signal_error(MYNAME": no size given");
|
||||||
size = ((size==0) ? 1 : size) * ((num==0) ? 1 : num);
|
size = ((size==0) ? 1 : size) * ((num==0) ? 1 : num);
|
||||||
if (mode == NULL)
|
if (mode == NULL)
|
||||||
mf = (base != NULL && CTYPE_PRIMTYPE(base) == &ffi_type_pointer)
|
mf = (base != NULL && CTYPE_PRIMTYPE(base) == &ffi_type_gcpointer)
|
||||||
? scheme_malloc : scheme_malloc_atomic;
|
? scheme_malloc : scheme_malloc_atomic;
|
||||||
else if (SAME_OBJ(mode, nonatomic_sym)) mf = scheme_malloc;
|
else if (SAME_OBJ(mode, nonatomic_sym)) mf = scheme_malloc;
|
||||||
else if (SAME_OBJ(mode, atomic_sym)) mf = scheme_malloc_atomic;
|
else if (SAME_OBJ(mode, atomic_sym)) mf = scheme_malloc_atomic;
|
||||||
|
@ -1324,7 +1336,10 @@ static void* SCHEME2C(Scheme_Object *type, void *dst, long delta,
|
||||||
if (failok) res = scheme_malloc_fail_ok(mf,size); else res = mf(size);
|
if (failok) res = scheme_malloc_fail_ok(mf,size); else res = mf(size);
|
||||||
if (((from != NULL) || (foff != 0)) && (res != NULL))
|
if (((from != NULL) || (foff != 0)) && (res != NULL))
|
||||||
memcpy(res, W_OFFSET(from, foff), size);
|
memcpy(res, W_OFFSET(from, foff), size);
|
||||||
return scheme_make_foreign_cpointer(res);
|
if (SAME_OBJ(mode, raw_sym))
|
||||||
|
return scheme_make_foreign_external_cpointer(res);
|
||||||
|
else
|
||||||
|
return scheme_make_foreign_cpointer(res);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* (end-stubborn-change ptr) */
|
/* (end-stubborn-change ptr) */
|
||||||
|
@ -1359,7 +1374,7 @@ static void* SCHEME2C(Scheme_Object *type, void *dst, long delta,
|
||||||
|
|
||||||
/* (malloc-immobile-cell v) */
|
/* (malloc-immobile-cell v) */
|
||||||
@cdefine[malloc-immobile-cell 1]{
|
@cdefine[malloc-immobile-cell 1]{
|
||||||
return scheme_make_foreign_cpointer(scheme_malloc_immobile_box(argv[0]));
|
return scheme_make_foreign_external_cpointer(scheme_malloc_immobile_box(argv[0]));
|
||||||
}
|
}
|
||||||
|
|
||||||
/* (free-immobile-cell b) */
|
/* (free-immobile-cell b) */
|
||||||
|
@ -1410,10 +1425,16 @@ static Scheme_Object *do_ptr_add(const char *who, int is_bang,
|
||||||
((Scheme_Offset_Cptr*)(argv[0]))->offset += noff;
|
((Scheme_Offset_Cptr*)(argv[0]))->offset += noff;
|
||||||
return scheme_void;
|
return scheme_void;
|
||||||
} else {
|
} else {
|
||||||
return scheme_make_offset_cptr
|
if (SCHEME_CPTRP(argv[0]) && (SCHEME_CPTR_FLAGS(argv[0]) & 0x1))
|
||||||
(SCHEME_FFIANYPTR_VAL(argv[0]),
|
return scheme_make_offset_external_cptr
|
||||||
SCHEME_FFIANYPTR_OFFSET(argv[0]) + noff,
|
(SCHEME_FFIANYPTR_VAL(argv[0]),
|
||||||
(SCHEME_CPTRP(argv[0])) ? SCHEME_CPTR_TYPE(argv[0]) : NULL);
|
SCHEME_FFIANYPTR_OFFSET(argv[0]) + noff,
|
||||||
|
(SCHEME_CPTRP(argv[0])) ? SCHEME_CPTR_TYPE(argv[0]) : NULL);
|
||||||
|
else
|
||||||
|
return scheme_make_offset_cptr
|
||||||
|
(SCHEME_FFIANYPTR_VAL(argv[0]),
|
||||||
|
SCHEME_FFIANYPTR_OFFSET(argv[0]) + noff,
|
||||||
|
(SCHEME_CPTRP(argv[0])) ? SCHEME_CPTR_TYPE(argv[0]) : NULL);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2112,6 +2133,7 @@ void scheme_init_foreign(Scheme_Env *env)
|
||||||
Scheme_Env *menv;
|
Scheme_Env *menv;
|
||||||
ctype_struct *t;
|
ctype_struct *t;
|
||||||
Scheme_Object *s;
|
Scheme_Object *s;
|
||||||
|
memcpy(&ffi_type_gcpointer, &ffi_type_pointer, sizeof(ffi_type_pointer));
|
||||||
menv = scheme_primitive_module(scheme_intern_symbol("#%foreign"), env);
|
menv = scheme_primitive_module(scheme_intern_symbol("#%foreign"), env);
|
||||||
@(maplines
|
@(maplines
|
||||||
(lambda (x)
|
(lambda (x)
|
||||||
|
|
|
@ -300,6 +300,8 @@ scheme_get_unsigned_long_long_val
|
||||||
scheme_real_to_double
|
scheme_real_to_double
|
||||||
scheme_make_cptr
|
scheme_make_cptr
|
||||||
scheme_make_offset_cptr
|
scheme_make_offset_cptr
|
||||||
|
scheme_make_external_cptr
|
||||||
|
scheme_make_offset_external_cptr
|
||||||
scheme_get_proc_name
|
scheme_get_proc_name
|
||||||
scheme_utf8_decode
|
scheme_utf8_decode
|
||||||
scheme_utf8_decode_as_prefix
|
scheme_utf8_decode_as_prefix
|
||||||
|
|
|
@ -311,6 +311,8 @@ scheme_get_unsigned_long_long_val
|
||||||
scheme_real_to_double
|
scheme_real_to_double
|
||||||
scheme_make_cptr
|
scheme_make_cptr
|
||||||
scheme_make_offset_cptr
|
scheme_make_offset_cptr
|
||||||
|
scheme_make_external_cptr
|
||||||
|
scheme_make_offset_external_cptr
|
||||||
scheme_get_proc_name
|
scheme_get_proc_name
|
||||||
scheme_utf8_decode
|
scheme_utf8_decode
|
||||||
scheme_utf8_decode_as_prefix
|
scheme_utf8_decode_as_prefix
|
||||||
|
|
|
@ -288,6 +288,8 @@ EXPORTS
|
||||||
scheme_real_to_double
|
scheme_real_to_double
|
||||||
scheme_make_cptr
|
scheme_make_cptr
|
||||||
scheme_make_offset_cptr
|
scheme_make_offset_cptr
|
||||||
|
scheme_make_external_cptr
|
||||||
|
scheme_make_offset_external_cptr
|
||||||
scheme_get_proc_name
|
scheme_get_proc_name
|
||||||
scheme_utf8_decode
|
scheme_utf8_decode
|
||||||
scheme_utf8_decode_as_prefix
|
scheme_utf8_decode_as_prefix
|
||||||
|
|
|
@ -303,6 +303,8 @@ EXPORTS
|
||||||
scheme_real_to_double
|
scheme_real_to_double
|
||||||
scheme_make_cptr
|
scheme_make_cptr
|
||||||
scheme_make_offset_cptr
|
scheme_make_offset_cptr
|
||||||
|
scheme_make_external_cptr
|
||||||
|
scheme_make_offset_external_cptr
|
||||||
scheme_get_proc_name
|
scheme_get_proc_name
|
||||||
scheme_utf8_decode
|
scheme_utf8_decode
|
||||||
scheme_utf8_decode_as_prefix
|
scheme_utf8_decode_as_prefix
|
||||||
|
|
|
@ -564,7 +564,7 @@ typedef long (*Scheme_Secondary_Hash_Proc)(Scheme_Object *obj, void *cycle_data)
|
||||||
|
|
||||||
typedef struct Scheme_Cptr
|
typedef struct Scheme_Cptr
|
||||||
{
|
{
|
||||||
Scheme_Object so;
|
Scheme_Inclhash_Object so; /* 0x1 => an external pointer (not GCable) */
|
||||||
void *val;
|
void *val;
|
||||||
Scheme_Object *type;
|
Scheme_Object *type;
|
||||||
} Scheme_Cptr;
|
} Scheme_Cptr;
|
||||||
|
@ -577,6 +577,7 @@ typedef struct Scheme_Offset_Cptr
|
||||||
#define SCHEME_CPTR_VAL(obj) (((Scheme_Cptr *)(obj))->val)
|
#define SCHEME_CPTR_VAL(obj) (((Scheme_Cptr *)(obj))->val)
|
||||||
#define SCHEME_CPTR_TYPE(obj) (((Scheme_Cptr *)(obj))->type)
|
#define SCHEME_CPTR_TYPE(obj) (((Scheme_Cptr *)(obj))->type)
|
||||||
#define SCHEME_CPTR_OFFSET(obj) (SAME_TYPE(_SCHEME_TYPE(obj), scheme_offset_cpointer_type) ? ((Scheme_Offset_Cptr *)obj)->offset : 0)
|
#define SCHEME_CPTR_OFFSET(obj) (SAME_TYPE(_SCHEME_TYPE(obj), scheme_offset_cpointer_type) ? ((Scheme_Offset_Cptr *)obj)->offset : 0)
|
||||||
|
#define SCHEME_CPTR_FLAGS(obj) MZ_OPT_HASH_KEY(&((Scheme_Cptr *)(obj))->so)
|
||||||
|
|
||||||
#define SCHEME_SET_IMMUTABLE(obj) ((MZ_OPT_HASH_KEY((Scheme_Inclhash_Object *)(obj)) |= 0x1))
|
#define SCHEME_SET_IMMUTABLE(obj) ((MZ_OPT_HASH_KEY((Scheme_Inclhash_Object *)(obj)) |= 0x1))
|
||||||
#define SCHEME_SET_CHAR_STRING_IMMUTABLE(obj) SCHEME_SET_IMMUTABLE(obj)
|
#define SCHEME_SET_CHAR_STRING_IMMUTABLE(obj) SCHEME_SET_IMMUTABLE(obj)
|
||||||
|
|
|
@ -156,14 +156,18 @@ static int cpointer_obj_SIZE(void *p) {
|
||||||
}
|
}
|
||||||
|
|
||||||
static int cpointer_obj_MARK(void *p) {
|
static int cpointer_obj_MARK(void *p) {
|
||||||
gcMARK(SCHEME_CPTR_VAL(p));
|
if (!(SCHEME_CPTR_FLAGS(p) & 0x1)) {
|
||||||
|
gcMARK(SCHEME_CPTR_VAL(p));
|
||||||
|
}
|
||||||
gcMARK(SCHEME_CPTR_TYPE(p));
|
gcMARK(SCHEME_CPTR_TYPE(p));
|
||||||
return
|
return
|
||||||
gcBYTES_TO_WORDS(sizeof(Scheme_Cptr));
|
gcBYTES_TO_WORDS(sizeof(Scheme_Cptr));
|
||||||
}
|
}
|
||||||
|
|
||||||
static int cpointer_obj_FIXUP(void *p) {
|
static int cpointer_obj_FIXUP(void *p) {
|
||||||
gcFIXUP(SCHEME_CPTR_VAL(p));
|
if (!(SCHEME_CPTR_FLAGS(p) & 0x1)) {
|
||||||
|
gcFIXUP(SCHEME_CPTR_VAL(p));
|
||||||
|
}
|
||||||
gcFIXUP(SCHEME_CPTR_TYPE(p));
|
gcFIXUP(SCHEME_CPTR_TYPE(p));
|
||||||
return
|
return
|
||||||
gcBYTES_TO_WORDS(sizeof(Scheme_Cptr));
|
gcBYTES_TO_WORDS(sizeof(Scheme_Cptr));
|
||||||
|
@ -179,14 +183,18 @@ static int offset_cpointer_obj_SIZE(void *p) {
|
||||||
}
|
}
|
||||||
|
|
||||||
static int offset_cpointer_obj_MARK(void *p) {
|
static int offset_cpointer_obj_MARK(void *p) {
|
||||||
gcMARK(SCHEME_CPTR_VAL(p));
|
if (!(SCHEME_CPTR_FLAGS(p) & 0x1)) {
|
||||||
|
gcMARK(SCHEME_CPTR_VAL(p));
|
||||||
|
}
|
||||||
gcMARK(SCHEME_CPTR_TYPE(p));
|
gcMARK(SCHEME_CPTR_TYPE(p));
|
||||||
return
|
return
|
||||||
gcBYTES_TO_WORDS(sizeof(Scheme_Offset_Cptr));
|
gcBYTES_TO_WORDS(sizeof(Scheme_Offset_Cptr));
|
||||||
}
|
}
|
||||||
|
|
||||||
static int offset_cpointer_obj_FIXUP(void *p) {
|
static int offset_cpointer_obj_FIXUP(void *p) {
|
||||||
gcFIXUP(SCHEME_CPTR_VAL(p));
|
if (!(SCHEME_CPTR_FLAGS(p) & 0x1)) {
|
||||||
|
gcFIXUP(SCHEME_CPTR_VAL(p));
|
||||||
|
}
|
||||||
gcFIXUP(SCHEME_CPTR_TYPE(p));
|
gcFIXUP(SCHEME_CPTR_TYPE(p));
|
||||||
return
|
return
|
||||||
gcBYTES_TO_WORDS(sizeof(Scheme_Offset_Cptr));
|
gcBYTES_TO_WORDS(sizeof(Scheme_Offset_Cptr));
|
||||||
|
|
|
@ -56,7 +56,9 @@ quotesyntax_obj {
|
||||||
|
|
||||||
cpointer_obj {
|
cpointer_obj {
|
||||||
mark:
|
mark:
|
||||||
gcMARK(SCHEME_CPTR_VAL(p));
|
if (!(SCHEME_CPTR_FLAGS(p) & 0x1)) {
|
||||||
|
gcMARK(SCHEME_CPTR_VAL(p));
|
||||||
|
}
|
||||||
gcMARK(SCHEME_CPTR_TYPE(p));
|
gcMARK(SCHEME_CPTR_TYPE(p));
|
||||||
size:
|
size:
|
||||||
gcBYTES_TO_WORDS(sizeof(Scheme_Cptr));
|
gcBYTES_TO_WORDS(sizeof(Scheme_Cptr));
|
||||||
|
@ -64,7 +66,9 @@ cpointer_obj {
|
||||||
|
|
||||||
offset_cpointer_obj {
|
offset_cpointer_obj {
|
||||||
mark:
|
mark:
|
||||||
gcMARK(SCHEME_CPTR_VAL(p));
|
if (!(SCHEME_CPTR_FLAGS(p) & 0x1)) {
|
||||||
|
gcMARK(SCHEME_CPTR_VAL(p));
|
||||||
|
}
|
||||||
gcMARK(SCHEME_CPTR_TYPE(p));
|
gcMARK(SCHEME_CPTR_TYPE(p));
|
||||||
size:
|
size:
|
||||||
gcBYTES_TO_WORDS(sizeof(Scheme_Offset_Cptr));
|
gcBYTES_TO_WORDS(sizeof(Scheme_Offset_Cptr));
|
||||||
|
|
|
@ -342,6 +342,14 @@ Scheme_Object *scheme_make_cptr(void *cptr, Scheme_Object *typetag)
|
||||||
return o;
|
return o;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Scheme_Object *scheme_make_external_cptr(GC_CAN_IGNORE void *cptr, Scheme_Object *typetag)
|
||||||
|
{
|
||||||
|
Scheme_Object *o;
|
||||||
|
o = scheme_make_cptr(NULL, typetag);
|
||||||
|
SCHEME_CPTR_VAL(o) = cptr;
|
||||||
|
return o;
|
||||||
|
}
|
||||||
|
|
||||||
Scheme_Object *scheme_make_offset_cptr(void *cptr, long offset, Scheme_Object *typetag)
|
Scheme_Object *scheme_make_offset_cptr(void *cptr, long offset, Scheme_Object *typetag)
|
||||||
{
|
{
|
||||||
Scheme_Object *o;
|
Scheme_Object *o;
|
||||||
|
@ -355,6 +363,15 @@ Scheme_Object *scheme_make_offset_cptr(void *cptr, long offset, Scheme_Object *t
|
||||||
return o;
|
return o;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Scheme_Object *scheme_make_offset_external_cptr(GC_CAN_IGNORE void *cptr, long offset, Scheme_Object *typetag)
|
||||||
|
{
|
||||||
|
Scheme_Object *o;
|
||||||
|
o = scheme_make_offset_cptr(NULL, offset, typetag);
|
||||||
|
SCHEME_CPTR_VAL(o) = cptr;
|
||||||
|
return o;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/************************************************************************/
|
/************************************************************************/
|
||||||
/* allocation */
|
/* allocation */
|
||||||
/************************************************************************/
|
/************************************************************************/
|
||||||
|
|
|
@ -576,6 +576,8 @@ XFORM_NONGCING MZ_EXTERN double scheme_real_to_double(Scheme_Object *r);
|
||||||
|
|
||||||
MZ_EXTERN Scheme_Object *scheme_make_cptr(void *cptr, Scheme_Object *typetag);
|
MZ_EXTERN Scheme_Object *scheme_make_cptr(void *cptr, Scheme_Object *typetag);
|
||||||
MZ_EXTERN Scheme_Object *scheme_make_offset_cptr(void *cptr, long offset, Scheme_Object *typetag);
|
MZ_EXTERN Scheme_Object *scheme_make_offset_cptr(void *cptr, long offset, Scheme_Object *typetag);
|
||||||
|
MZ_EXTERN Scheme_Object *scheme_make_external_cptr(void *cptr, Scheme_Object *typetag);
|
||||||
|
MZ_EXTERN Scheme_Object *scheme_make_offset_external_cptr(void *cptr, long offset, Scheme_Object *typetag);
|
||||||
|
|
||||||
MZ_EXTERN const char *scheme_get_proc_name(Scheme_Object *p, int *len, int for_error);
|
MZ_EXTERN const char *scheme_get_proc_name(Scheme_Object *p, int *len, int for_error);
|
||||||
|
|
||||||
|
|
|
@ -475,6 +475,8 @@ int (*scheme_get_unsigned_long_long_val)(Scheme_Object *o, umzlonglong *v);
|
||||||
double (*scheme_real_to_double)(Scheme_Object *r);
|
double (*scheme_real_to_double)(Scheme_Object *r);
|
||||||
Scheme_Object *(*scheme_make_cptr)(void *cptr, Scheme_Object *typetag);
|
Scheme_Object *(*scheme_make_cptr)(void *cptr, Scheme_Object *typetag);
|
||||||
Scheme_Object *(*scheme_make_offset_cptr)(void *cptr, long offset, Scheme_Object *typetag);
|
Scheme_Object *(*scheme_make_offset_cptr)(void *cptr, long offset, Scheme_Object *typetag);
|
||||||
|
Scheme_Object *(*scheme_make_external_cptr)(void *cptr, Scheme_Object *typetag);
|
||||||
|
Scheme_Object *(*scheme_make_offset_external_cptr)(void *cptr, long offset, Scheme_Object *typetag);
|
||||||
const char *(*scheme_get_proc_name)(Scheme_Object *p, int *len, int for_error);
|
const char *(*scheme_get_proc_name)(Scheme_Object *p, int *len, int for_error);
|
||||||
/*========================================================================*/
|
/*========================================================================*/
|
||||||
/* strings */
|
/* strings */
|
||||||
|
|
|
@ -337,6 +337,8 @@
|
||||||
scheme_extension_table->scheme_real_to_double = scheme_real_to_double;
|
scheme_extension_table->scheme_real_to_double = scheme_real_to_double;
|
||||||
scheme_extension_table->scheme_make_cptr = scheme_make_cptr;
|
scheme_extension_table->scheme_make_cptr = scheme_make_cptr;
|
||||||
scheme_extension_table->scheme_make_offset_cptr = scheme_make_offset_cptr;
|
scheme_extension_table->scheme_make_offset_cptr = scheme_make_offset_cptr;
|
||||||
|
scheme_extension_table->scheme_make_external_cptr = scheme_make_external_cptr;
|
||||||
|
scheme_extension_table->scheme_make_offset_external_cptr = scheme_make_offset_external_cptr;
|
||||||
scheme_extension_table->scheme_get_proc_name = scheme_get_proc_name;
|
scheme_extension_table->scheme_get_proc_name = scheme_get_proc_name;
|
||||||
scheme_extension_table->scheme_utf8_decode = scheme_utf8_decode;
|
scheme_extension_table->scheme_utf8_decode = scheme_utf8_decode;
|
||||||
scheme_extension_table->scheme_utf8_decode_as_prefix = scheme_utf8_decode_as_prefix;
|
scheme_extension_table->scheme_utf8_decode_as_prefix = scheme_utf8_decode_as_prefix;
|
||||||
|
|
|
@ -337,6 +337,8 @@
|
||||||
#define scheme_real_to_double (scheme_extension_table->scheme_real_to_double)
|
#define scheme_real_to_double (scheme_extension_table->scheme_real_to_double)
|
||||||
#define scheme_make_cptr (scheme_extension_table->scheme_make_cptr)
|
#define scheme_make_cptr (scheme_extension_table->scheme_make_cptr)
|
||||||
#define scheme_make_offset_cptr (scheme_extension_table->scheme_make_offset_cptr)
|
#define scheme_make_offset_cptr (scheme_extension_table->scheme_make_offset_cptr)
|
||||||
|
#define scheme_make_external_cptr (scheme_extension_table->scheme_make_external_cptr)
|
||||||
|
#define scheme_make_offset_external_cptr (scheme_extension_table->scheme_make_offset_external_cptr)
|
||||||
#define scheme_get_proc_name (scheme_extension_table->scheme_get_proc_name)
|
#define scheme_get_proc_name (scheme_extension_table->scheme_get_proc_name)
|
||||||
#define scheme_utf8_decode (scheme_extension_table->scheme_utf8_decode)
|
#define scheme_utf8_decode (scheme_extension_table->scheme_utf8_decode)
|
||||||
#define scheme_utf8_decode_as_prefix (scheme_extension_table->scheme_utf8_decode_as_prefix)
|
#define scheme_utf8_decode_as_prefix (scheme_extension_table->scheme_utf8_decode_as_prefix)
|
||||||
|
|
|
@ -13,12 +13,12 @@
|
||||||
consistently.)
|
consistently.)
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#define MZSCHEME_VERSION "4.2.2.5"
|
#define MZSCHEME_VERSION "4.2.2.6"
|
||||||
|
|
||||||
#define MZSCHEME_VERSION_X 4
|
#define MZSCHEME_VERSION_X 4
|
||||||
#define MZSCHEME_VERSION_Y 2
|
#define MZSCHEME_VERSION_Y 2
|
||||||
#define MZSCHEME_VERSION_Z 2
|
#define MZSCHEME_VERSION_Z 2
|
||||||
#define MZSCHEME_VERSION_W 5
|
#define MZSCHEME_VERSION_W 6
|
||||||
|
|
||||||
#define MZSCHEME_VERSION_MAJOR ((MZSCHEME_VERSION_X * 100) + MZSCHEME_VERSION_Y)
|
#define MZSCHEME_VERSION_MAJOR ((MZSCHEME_VERSION_X * 100) + MZSCHEME_VERSION_Y)
|
||||||
#define MZSCHEME_VERSION_MINOR ((MZSCHEME_VERSION_Z * 1000) + MZSCHEME_VERSION_W)
|
#define MZSCHEME_VERSION_MINOR ((MZSCHEME_VERSION_Z * 1000) + MZSCHEME_VERSION_W)
|
||||||
|
|
Loading…
Reference in New Issue
Block a user