mirror of
https://github.com/ashinn/chibi-scheme.git
synced 2025-07-11 23:17:34 +02:00
More documentation.
This commit is contained in:
parent
357684a730
commit
2cda6db130
8 changed files with 150 additions and 14 deletions
|
@ -1,7 +1,12 @@
|
|||
;; net.scm -- the high-level network interface
|
||||
;; Copyright (c) 2010 Alex Shinn. All rights reserved.
|
||||
;; Copyright (c) 2010-2011 Alex Shinn. All rights reserved.
|
||||
;; BSD-style license: http://synthcode.com/license.txt
|
||||
|
||||
;;> Opens a client net connection to @var{host}, a string,
|
||||
;;> on port @var{service}, which can be a string such as
|
||||
;;> @scheme{"http"} or an integer. Returns a list of two
|
||||
;;> values on success - an input port and output port -
|
||||
;;> or @scheme{#f} on failure.
|
||||
|
||||
(define (open-net-io host service)
|
||||
(let lp ((addr (get-address-info host
|
||||
(if (integer? service)
|
||||
|
@ -28,6 +33,13 @@
|
|||
(list (open-input-file-descriptor sock)
|
||||
(open-output-file-descriptor sock)))))))))
|
||||
|
||||
;;> Convenience wrapper around @scheme{open-net-io}, opens
|
||||
;;> the connection then calls @var{proc} with two arguments,
|
||||
;;> the input port and the output port connected to the
|
||||
;;> service, then closes the connection. Returns the result
|
||||
;;> of @var{proc}. Raises an error if a connection can't
|
||||
;;> be made.
|
||||
|
||||
(define (with-net-io host service proc)
|
||||
(let ((io (open-net-io host service)))
|
||||
(if (not (pair? io))
|
||||
|
|
|
@ -16,11 +16,31 @@
|
|||
(size_t ai_addrlen address-info-address-length)
|
||||
((link addrinfo) ai_next address-info-next))
|
||||
|
||||
;;> The addrinfo struct accessors.
|
||||
;;/
|
||||
|
||||
;;> Create and return a new addrinfo structure for the
|
||||
;;> given host and service.
|
||||
|
||||
(define-c errno (get-address-info getaddrinfo)
|
||||
(string string (maybe-null addrinfo) (result free addrinfo)))
|
||||
|
||||
;;> Bind a name to a socket.
|
||||
|
||||
(define-c int bind (int sockaddr int))
|
||||
|
||||
;;> Listen on a socket.
|
||||
|
||||
(define-c int listen (int int))
|
||||
(define-c int socket (int int int))
|
||||
(define-c int connect (int sockaddr int))
|
||||
|
||||
;;> Accept a connection on a socket.
|
||||
|
||||
(define-c int accept (int sockaddr (pointer unsigned)))
|
||||
|
||||
;;> Create an endpoint for communication.
|
||||
|
||||
(define-c int socket (int int int))
|
||||
|
||||
;;> Initiate a connection on a socket.
|
||||
|
||||
(define-c int connect (int sockaddr int))
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
|
||||
(module (chibi pathname)
|
||||
(export path-strip-directory path-directory path-extension-pos
|
||||
(export path-strip-directory path-directory ;; path-extension-pos
|
||||
path-extension path-strip-extension path-replace-extension
|
||||
path-absolute? path-relative? path-normalize make-path)
|
||||
(import-immutable (scheme))
|
||||
|
|
|
@ -1,7 +1,8 @@
|
|||
;; pathname.scm -- a general, non-host-specific path lib
|
||||
;; Copyright (c) 2009 Alex Shinn. All rights reserved.
|
||||
;; Copyright (c) 2009-2011 Alex Shinn. All rights reserved.
|
||||
;; BSD-style license: http://synthcode.com/license.txt
|
||||
|
||||
;;> A general, non-host-specific pathname library.
|
||||
|
||||
(define (string-scan c str . o)
|
||||
(let ((limit (string-length str)))
|
||||
(let lp ((i (if (pair? o) (car o) 0)))
|
||||
|
@ -38,6 +39,11 @@
|
|||
;; (let ((start (string-scan-right #\/ path (- end 1))))
|
||||
;; (substring path (if start (+ start 1) 0) (+ end 1)))))))
|
||||
|
||||
;;> Returns just the basename of @var{path}, with any directory
|
||||
;;> removed. If @var{path} does not contain a directory separator,
|
||||
;;> return the whole @var{path}. If @var{path} ends in a directory
|
||||
;;> separator (i.e. path is a directory) return the empty string.
|
||||
|
||||
;; GNU basename
|
||||
(define (path-strip-directory path)
|
||||
(if (string=? path "")
|
||||
|
@ -50,6 +56,9 @@
|
|||
path
|
||||
(substring path (+ slash 1) len)))))))
|
||||
|
||||
;;> Returns just the directory of @var{path}.
|
||||
;;> If @var{path} is relative, return @scheme{"."}.
|
||||
|
||||
(define (path-directory path)
|
||||
(if (string=? path "")
|
||||
"."
|
||||
|
@ -64,30 +73,50 @@
|
|||
|
||||
(define (path-extension-pos path) (string-scan-right #\. path))
|
||||
|
||||
;;> Returns the rightmost extension of @var{path}, not including
|
||||
;;> the @scheme{"."}. If there is no extension, returns @scheme{#f}.
|
||||
|
||||
(define (path-extension path)
|
||||
(let ((i (path-extension-pos path)))
|
||||
(and i
|
||||
(let ((start (+ i 1)) (end (string-length path)))
|
||||
(and (< start end) (substring path start end))))))
|
||||
|
||||
;;> Returns @var{path} with the extension, if any, removed,
|
||||
;;> along with the @scheme{"."}.
|
||||
|
||||
(define (path-strip-extension path)
|
||||
(let ((i (path-extension-pos path)))
|
||||
(if (and i (< (+ i 1) (string-length path)))
|
||||
(substring path 0 i)
|
||||
path)))
|
||||
|
||||
;;> Returns @var{path} with the extension, if any, replaced
|
||||
;;> with @var{ext}.
|
||||
|
||||
(define (path-replace-extension path ext)
|
||||
(string-append (path-strip-extension path) "." ext))
|
||||
|
||||
;;> Returns @scheme{#t} iff @var{path} is an absolute path.
|
||||
|
||||
(define (path-absolute? path)
|
||||
(and (not (string=? "" path)) (eqv? #\/ (string-ref path 0))))
|
||||
|
||||
;;> Returns @scheme{#t} iff @var{path} is a relative path.
|
||||
|
||||
(define (path-relative? path) (not (path-absolute? path)))
|
||||
|
||||
;; This looks big and hairy, but it's mutation-free and guarantees:
|
||||
;; (string=? s (path-normalize s)) <=> (eq? s (path-normalize s))
|
||||
;; i.e. fast and simple for already normalized paths.
|
||||
|
||||
;;> Returns a normalized version of path, with duplicate directory
|
||||
;;> separators removed and "/./" and "x/../" references removed.
|
||||
;;> Does not take symbolic links into account - this is meant to
|
||||
;;> be abstract and applicable to paths on remote systems and in
|
||||
;;> URIs. Returns @var{path} itself if @var{path} is already
|
||||
;;> normalized.
|
||||
|
||||
(define (path-normalize path)
|
||||
(let* ((len (string-length path)) (len-1 (- len 1)))
|
||||
(define (collect i j res)
|
||||
|
@ -155,6 +184,9 @@
|
|||
path
|
||||
((if (eqv? #\/ (string-ref path 0)) boundary inside) 0 1 '()))))
|
||||
|
||||
;;> Return a new string representing the path where each of @var{args}
|
||||
;;> is a path component, separated with the directory separator.
|
||||
|
||||
(define (make-path . args)
|
||||
(define (x->string x)
|
||||
(cond ((string? x) x)
|
||||
|
|
|
@ -14,33 +14,59 @@
|
|||
(int tm_yday time-day-of-year)
|
||||
(int tm_isdst time-dst?))
|
||||
|
||||
;;> Accessors for the @scheme{tm} struct.
|
||||
;;/
|
||||
|
||||
(define-c-struct timeval
|
||||
predicate: timeval?
|
||||
(time_t tv_sec timeval-seconds)
|
||||
(int tv_usec timeval-microseconds))
|
||||
|
||||
;;> Accessors for the @scheme{timeval} struct.
|
||||
;;/
|
||||
|
||||
(define-c-struct timezone
|
||||
predicate: timezone?
|
||||
(int tz_minuteswest timezone-offset)
|
||||
(int tz_dsttime timezone-dst-time))
|
||||
|
||||
;;> Accessors for the @scheme{timezone} struct.
|
||||
;;/
|
||||
|
||||
;;> Returns the current time as an integer number
|
||||
;;> of seconds since an arbitrary epoch.
|
||||
|
||||
(define-c time_t (current-seconds "time") ((value NULL)))
|
||||
|
||||
;;> Returns the current time as a list of a timeval struct
|
||||
;;> and a timezone.
|
||||
|
||||
(define-c errno (get-time-of-day "gettimeofday")
|
||||
((result timeval) (result timezone)))
|
||||
|
||||
;;> Set the current time from a timeval struct and
|
||||
;;> and optional timezone.
|
||||
|
||||
(define-c errno (set-time-of-day! "settimeofday")
|
||||
(timeval (maybe-null default NULL timezone)))
|
||||
|
||||
;;> Convert an integer number of epoch seconds to a broken-down tm struct.
|
||||
|
||||
(define-c non-null-pointer (seconds->time "localtime_r")
|
||||
((pointer time_t) (result tm)))
|
||||
|
||||
;;> Convert a tm struct to an integer number of seconds.
|
||||
|
||||
(define-c time_t (time->seconds "mktime")
|
||||
(tm))
|
||||
|
||||
;;> Format a datetime string from an integer number of epoch seconds.
|
||||
|
||||
(define-c non-null-string (seconds->string "ctime_r")
|
||||
((pointer time_t) (result (array char 64))))
|
||||
|
||||
;;> Format a datetime string from a tm struct.
|
||||
|
||||
(define-c non-null-string (time->string "asctime_r")
|
||||
(tm (result (array char 64))))
|
||||
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
;; type-inference.scm -- general type-inference for Scheme
|
||||
;;
|
||||
;; Copyright (c) 2010 Alex Shinn. All rights reserved.
|
||||
;; Copyright (c) 2010-2011 Alex Shinn. All rights reserved.
|
||||
;; BSD-style license: http://synthcode.com/license.txt
|
||||
|
||||
;;> General type-inference library.
|
||||
|
||||
(define (typed? x)
|
||||
(and (lambda? x)
|
||||
(lambda-return-type x)))
|
||||
|
@ -226,6 +226,8 @@
|
|||
(for-each type-analyze-expr ls)
|
||||
(for-each type-resolve-circularities ls))
|
||||
|
||||
;;> Analyze the types of all bindings in the module @var{name}.
|
||||
|
||||
(define (type-analyze-module name)
|
||||
(let* ((mod (analyze-module name))
|
||||
(ls (and (vector? mod) (module-ast mod))))
|
||||
|
@ -240,6 +242,9 @@
|
|||
(type-analyze-module-body name ls))
|
||||
ls))))
|
||||
|
||||
;;> Return the type signature for a given source
|
||||
;;> code expression.
|
||||
|
||||
(define (type-analyze sexp . o)
|
||||
(type-analyze-expr (apply analyze sexp o)))
|
||||
|
||||
|
@ -255,6 +260,10 @@
|
|||
(define (lambda-type x)
|
||||
(cons 'lambda (cons (lambda-return-type x) (lambda-param-types x))))
|
||||
|
||||
;;> Return the type signature for the procedure @var{x} as
|
||||
;;> a list whose first element is the return type and whose
|
||||
;;> remaining arguments are the parameter types.
|
||||
|
||||
(define (procedure-signature x)
|
||||
(cond
|
||||
((opcode? x)
|
||||
|
|
|
@ -1,7 +1,8 @@
|
|||
;; uri.scm -- URI parsing library
|
||||
;; Copyright (c) 2009 Alex Shinn. All rights reserved.
|
||||
;; Copyright (c) 2009-2011 Alex Shinn. All rights reserved.
|
||||
;; BSD-style license: http://synthcode.com/license.txt
|
||||
|
||||
;;> Library for parsing and constructing URI objects.
|
||||
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; URI representation
|
||||
|
||||
|
@ -16,7 +17,11 @@
|
|||
(query uri-query)
|
||||
(fragment uri-fragment))
|
||||
|
||||
;; (make-uri scheme [user host port path query fragment])
|
||||
;;> Accessors for the URI type.
|
||||
;;/
|
||||
|
||||
;;> @subsubsubsection{@scheme{(make-uri scheme [user host port path query fragment])}}
|
||||
|
||||
(define (make-uri scheme . o)
|
||||
(let* ((user (if (pair? o) (car o) #f))
|
||||
(o (if (pair? o) (cdr o) '()))
|
||||
|
@ -81,7 +86,6 @@
|
|||
(lp (+ i 1)))))))
|
||||
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; functional updaters (uses as much shared state as possible)
|
||||
|
||||
(define (uri-with-scheme u scheme)
|
||||
(%make-uri scheme (uri-user u) (uri-host u) (uri-port u)
|
||||
|
@ -111,6 +115,10 @@
|
|||
(%make-uri (uri-scheme u) (uri-user u) (uri-host u) (uri-port u)
|
||||
(uri-path u) (uri-query u) fragment))
|
||||
|
||||
;;> Functional updaters - returns a new uri identical to @var{u}
|
||||
;;> with only the specified field changed.
|
||||
;;/
|
||||
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; parsing - without :// we just split into scheme & path
|
||||
|
||||
|
@ -181,9 +189,13 @@
|
|||
(decode (substring str (+ pound 1) len)))
|
||||
))))))))))
|
||||
|
||||
;;> Parses a string and returns a new URI object.
|
||||
|
||||
(define (string->uri str . o)
|
||||
(apply string->path-uri #f str o))
|
||||
|
||||
;;> Convert a URI object to a string.
|
||||
|
||||
(define (uri->string uri . o)
|
||||
(define encode? (and (pair? o) (car o)))
|
||||
(define encode (if encode? uri-encode (lambda (x) x)))
|
||||
|
@ -221,6 +233,12 @@
|
|||
res
|
||||
(cons (substring str from to) res)))
|
||||
|
||||
;;> @subsubsubsection{@scheme{(uri-encode str [plus?])}}
|
||||
|
||||
;;> Return the URI encoded version of the string @var{str},
|
||||
;;> using hex escapes as needed and replacing spaces with "+"
|
||||
;;> iff the optional argument @var{plus?} is true.
|
||||
|
||||
(define (uri-encode str . o)
|
||||
(define (encode-1-space ch)
|
||||
(if (eqv? ch #\space)
|
||||
|
@ -249,6 +267,12 @@
|
|||
(lp next next (cons (encode-1 ch)
|
||||
(collect str from to res)))))))))
|
||||
|
||||
;;> @subsubsubsection{@scheme{(uri-decode str [plus?])}}
|
||||
|
||||
;;> Decodes any URI hex escapes in the given string, and
|
||||
;;> translates any pluses ("+") to space iff the optional
|
||||
;;> argument @var{plus?} is true.
|
||||
|
||||
(define (uri-decode str . o)
|
||||
(let ((space-as-plus? (and (pair? o) (car o)))
|
||||
(start 0)
|
||||
|
@ -277,6 +301,12 @@
|
|||
(else
|
||||
(lp from next res))))))))
|
||||
|
||||
;;> @subsubsubsection{@scheme{(uri-query->alist str [plus?])}}
|
||||
|
||||
;;> Parses the query part of a URI as a delimited list of
|
||||
;;> URI encoded @rawcode{VAR=VALUE} pairs, decodes them and
|
||||
;;> returns the result as an alist.
|
||||
|
||||
(define (uri-query->alist str . o)
|
||||
(define (split-char? c) (if (eqv? c #\&) #t (eqv? c #\;)))
|
||||
(let ((len (string-length str))
|
||||
|
@ -292,6 +322,11 @@
|
|||
(cons (uri-decode (substring str i j) plus?) #f))))
|
||||
(lp (+ j 1) (cons cell res)))))))
|
||||
|
||||
;;> @subsubsubsection{@scheme{(uri-alist->query ls [plus?])}}
|
||||
|
||||
;;> The reverse of the above, formats the alist as a URI
|
||||
;;> query string.
|
||||
|
||||
(define (uri-alist->query ls . o)
|
||||
(define plus? (and (pair? o) (car o)))
|
||||
(define (encode key val res)
|
||||
|
|
|
@ -1,4 +1,6 @@
|
|||
|
||||
;;> Library for weak data structures.
|
||||
|
||||
(module (chibi weak)
|
||||
(export make-ephemeron ephemeron? ephemeron-broken?
|
||||
ephemeron-key ephemeron-value
|
||||
|
|
Loading…
Add table
Reference in a new issue