scheme-libraries/foreign/c/ironscheme-primitives.sld

141 lines
4.5 KiB
Scheme

(define-library
(foreign c ironscheme-primitives)
(import (rnrs base)
(rnrs lists)
(rnrs control)
(rnrs files)
(rnrs io simple)
(rnrs programs)
(only (rnrs bytevectors)
make-bytevector
bytevector-length
utf8->string
string->utf8
bytevector-u8-ref
bytevector-u8-set!)
(only (rnrs r5rs)
remainder
quotient)
(ironscheme)
(ironscheme clr)
(ironscheme clr internal)
(ironscheme ffi)
(srfi :0))
(export primitives-init
size-of-type
align-of-type
shared-object-load
define-c-procedure
c-bytevector?
c-bytevector-u8-ref
c-bytevector-u8-set!
c-bytevector-pointer-ref
c-bytevector-pointer-set!
make-c-null
c-null?)
(begin
(clr-using System.Runtime.InteropServices)
(define (primitives-init set-procedure get-procedure) #t)
;; FIXME
(define size-of-type
(lambda (type)
(cond ((eq? type 'i8) 1)
((eq? type 'u8) 1)
((eq? type 'i16) 2)
((eq? type 'u16) 2)
((eq? type 'i32) 4)
((eq? type 'u32) 4)
((eq? type 'i64) 8)
((eq? type 'u64) 8)
((eq? type 'char) 1)
((eq? type 'uchar) 1)
((eq? type 'short) 2)
((eq? type 'ushort) 2)
((eq? type 'int) 4)
((eq? type 'unsigned-int) 4)
((eq? type 'long) 8)
((eq? type 'ulong) 8)
((eq? type 'float) 4)
((eq? type 'double) 8)
((eq? type 'pointer) 8)
((eq? type 'void) 0)
(else #f))))
;; FIXME
(define align-of-type size-of-type)
;; FIXME
(define (type->native-type type)
(cond ((equal? type 'i8) 'int8)
((equal? type 'u8) 'uint8)
((equal? type 'i16) 'int16)
((equal? type 'u16) 'uint16)
((equal? type 'i32) 'int32)
((equal? type 'u32) 'uint32)
((equal? type 'i64) 'in64)
((equal? type 'u64) 'uint64)
((equal? type 'char) 'char)
((equal? type 'uchar) 'uchar)
((equal? type 'short) 'int16)
((equal? type 'ushort) 'uint16)
((equal? type 'int) 'int32)
((equal? type 'uint) 'uint32)
((equal? type 'long) 'int64)
((equal? type 'ulong) 'uint64)
((equal? type 'float) 'float)
((equal? type 'double) 'double)
((equal? type 'void) 'void)
((equal? type 'pointer) 'void*)
(error "Unsupported type: " type)))
(define c-bytevector?
(lambda (object)
(pointer? object)))
(define-syntax define-c-procedure
(syntax-rules ()
((_ scheme-name shared-object c-name return-type argument-types)
(define scheme-name
((make-ffi-callout (type->native-type return-type)
(map type->native-type argument-types))
(cond-expand
(windows (dlsym shared-object (symbol->string c-name)))
(else (apply (pinvoke-call libc dlsym void* (void* string))
(list shared-object (symbol->string c-name))))))))))
(define shared-object-load
(lambda (path options)
(cond-expand
(windows (dlopen path))
(else (apply (pinvoke-call libc dlopen void* (string int))
(list path 0))))))
(define c-bytevector-u8-set!
(lambda (c-bytevector k byte)
(clr-static-call Marshal
(WriteByte IntPtr Int32 Byte)
c-bytevector
k
(clr-static-call Convert (ToByte Int32) byte))))
(define c-bytevector-u8-ref
(lambda (c-bytevector k)
(clr-static-call Convert
(ToInt32 Byte)
(clr-static-call Marshal (ReadByte IntPtr Int32) c-bytevector k))))
(define c-bytevector-pointer-set!
(lambda (c-bytevector k pointer)
(write-intptr! c-bytevector k pointer)))
(define c-bytevector-pointer-ref
(lambda (c-bytevector k)
(read-intptr c-bytevector k)))
(define make-c-null null-pointer)
(define (c-null? pointer)
(and (pointer? pointer)
(null-pointer? pointer)))))