[gambit-list] newbie question: output from one port as input to another port
Marc Feeley
feeley at iro.umontreal.ca
Sun Mar 12 08:43:26 EST 2006
On 11-Mar-06, at 10:40 PM, Samuel Montgomery-Blinn wrote:
> So, I have been trying to learn Gambit-C's port mechanisms. This is
> likely an infantile question, but it seems that it should be the
> most basic thing to be able to take one input port and "connect" it
> to an output port. The specific use for me is sending the contents
> of a file over a network (tcp) port. I have tried a few methods,
> mostly "busy" and likely lossy methods.
>
> 1. read the entire contents of the file port, then output the file
> to the network port. (wastes time in which earlier parts of the
> file could be written to the network port)
> 2. read a line from the file port, and output the line to the
> network port. repeat until eof. (wastes time for many reasons)
>
> I was guessing that something to do with the procedures "call-with-
> input-file" or "with-output-to-file" might be something towards
> what might be most succinctly expressed as some sort of UNIX
> "sendfile" functionality, but as I am new both to Scheme (or any
> Lisp for that matter) and Gambit-C, I thought I would both say
> "hello" to this list and ask for its help and guidance. If this
> sort of question is not a faux pas, I certainly have more!
>
> -Sam
> _______________________________________________
> Gambit-list mailing list
> Gambit-list at iro.umontreal.ca
> http://mailman.iro.umontreal.ca/mailman/listinfo/gambit-list
Well, Christian just beat me to it, but here's my version anyway
(which shows off binary I/O as well as text I/O which is useful if
you are converting character and end-of-line encodings).
Marc
(define (copy-octet-port-to-octet-port in out)
(let ((buf (make-u8vector 4096)))
(let loop ()
(let ((n (read-subu8vector buf 0 (u8vector-length buf) in)))
(if (> n 0)
(begin
(write-subu8vector buf 0 n out)
(loop)))))))
(define (copy-char-port-to-char-port in out)
(let ((buf (make-string 4096)))
(let loop ()
(let ((n (read-substring buf 0 (string-length buf) in)))
(if (> n 0)
(begin
(write-substring buf 0 n out)
(loop)))))))
(define (copy-binary-file in-filename out-filename)
(call-with-input-file in-filename
(lambda (in)
(call-with-output-file out-filename
(lambda (out)
(copy-octet-port-to-octet-port in out))))))
(define (copy-text-file in-filename out-filename)
(call-with-input-file in-filename
(lambda (in)
(call-with-output-file out-filename
(lambda (out)
(copy-char-port-to-char-port in out))))))
(define (test)
; binary copy gsi/gsi -> gsi2
(time (copy-binary-file "gsi/gsi" "gsi2"))
; copy text file a.txt to b.txt, converting from UTF-8 character
; encoding (and any end-of-line encoding) to UCS-2 character
; encoding with BOM and DOS end-of-line encoding (compatible with
; Windows)
(time (copy-text-file
(list path: "a.txt" char-encoding: 'utf8 eol-encoding: 'cr-lf)
(list path: "b.txt" char-encoding: 'ucs2 eol-encoding: 'cr-
lf))))
(test)
More information about the Gambit-list
mailing list