Merge branch 'master' of git://factorcode.org/git/factor
commit
26ddc44dc0
|
@ -49,6 +49,9 @@ M: fd cancel-operation ( fd -- )
|
||||||
2bi
|
2bi
|
||||||
] if ;
|
] if ;
|
||||||
|
|
||||||
|
M: unix tell-handle ( handle -- n )
|
||||||
|
fd>> 0 SEEK_CUR lseek [ io-error ] [ ] bi ;
|
||||||
|
|
||||||
M: unix seek-handle ( n seek-type handle -- )
|
M: unix seek-handle ( n seek-type handle -- )
|
||||||
swap {
|
swap {
|
||||||
{ io:seek-absolute [ SEEK_SET ] }
|
{ io:seek-absolute [ SEEK_SET ] }
|
||||||
|
|
|
@ -124,8 +124,14 @@ M: output-port stream-write
|
||||||
|
|
||||||
HOOK: (wait-to-write) io-backend ( port -- )
|
HOOK: (wait-to-write) io-backend ( port -- )
|
||||||
|
|
||||||
|
HOOK: tell-handle os ( handle -- n )
|
||||||
HOOK: seek-handle os ( n seek-type handle -- )
|
HOOK: seek-handle os ( n seek-type handle -- )
|
||||||
|
|
||||||
|
M: buffered-port stream-tell ( stream -- n )
|
||||||
|
[ check-disposed ]
|
||||||
|
[ handle>> tell-handle ]
|
||||||
|
[ [ buffer>> size>> - 0 max ] [ buffer>> pos>> ] bi + ] tri ;
|
||||||
|
|
||||||
M: input-port stream-seek ( n seek-type stream -- )
|
M: input-port stream-seek ( n seek-type stream -- )
|
||||||
[ check-disposed ]
|
[ check-disposed ]
|
||||||
[ buffer>> 0 swap buffer-reset ]
|
[ buffer>> 0 swap buffer-reset ]
|
||||||
|
|
|
@ -44,4 +44,3 @@ M: duplex-stream underlying-handle
|
||||||
>duplex-stream<
|
>duplex-stream<
|
||||||
[ underlying-handle ] bi@
|
[ underlying-handle ] bi@
|
||||||
[ = [ invalid-duplex-stream ] when ] keep ;
|
[ = [ invalid-duplex-stream ] when ] keep ;
|
||||||
|
|
||||||
|
|
|
@ -24,7 +24,22 @@ HELP: limit
|
||||||
" \"123456\" <string-reader> 3 stream-throws limit"
|
" \"123456\" <string-reader> 3 stream-throws limit"
|
||||||
" 100 swap stream-read ."
|
" 100 swap stream-read ."
|
||||||
"] [ ] recover ."
|
"] [ ] recover ."
|
||||||
"T{ limit-exceeded }"
|
"""T{ limit-exceeded
|
||||||
|
{ n 1 }
|
||||||
|
{ stream
|
||||||
|
T{ limited-stream
|
||||||
|
{ stream
|
||||||
|
T{ string-reader
|
||||||
|
{ underlying "123456" }
|
||||||
|
{ i 3 }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
{ mode stream-throws }
|
||||||
|
{ count 4 }
|
||||||
|
{ limit 3 }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}"""
|
||||||
}
|
}
|
||||||
"Returning " { $link f } " on exhaustion:"
|
"Returning " { $link f } " on exhaustion:"
|
||||||
{ $example
|
{ $example
|
||||||
|
|
|
@ -1,7 +1,8 @@
|
||||||
USING: io io.streams.limited io.encodings io.encodings.string
|
USING: accessors continuations destructors io io.encodings
|
||||||
io.encodings.ascii io.encodings.binary io.streams.byte-array
|
io.encodings.8-bit io.encodings.ascii io.encodings.binary
|
||||||
namespaces tools.test strings kernel io.streams.string accessors
|
io.encodings.string io.encodings.utf8 io.files io.pipes
|
||||||
io.encodings.utf8 io.files destructors ;
|
io.streams.byte-array io.streams.limited io.streams.string
|
||||||
|
kernel namespaces strings tools.test system ;
|
||||||
IN: io.streams.limited.tests
|
IN: io.streams.limited.tests
|
||||||
|
|
||||||
[ ] [
|
[ ] [
|
||||||
|
@ -89,3 +90,127 @@ IN: io.streams.limited.tests
|
||||||
unlimited-input contents
|
unlimited-input contents
|
||||||
] with-input-stream
|
] with-input-stream
|
||||||
] unit-test
|
] unit-test
|
||||||
|
|
||||||
|
[ 4 ] [
|
||||||
|
"abcdefgh" <string-reader> 4 stream-throws <limited-stream> [
|
||||||
|
4 seek-relative seek-input tell-input
|
||||||
|
] with-input-stream
|
||||||
|
] unit-test
|
||||||
|
|
||||||
|
[
|
||||||
|
"abcdefgh" <string-reader> 4 stream-throws <limited-stream> [
|
||||||
|
4 seek-relative seek-input
|
||||||
|
4 read
|
||||||
|
] with-input-stream
|
||||||
|
] [
|
||||||
|
limit-exceeded?
|
||||||
|
] must-fail-with
|
||||||
|
|
||||||
|
[
|
||||||
|
"abcdefgh" <string-reader> 4 stream-throws <limited-stream> [
|
||||||
|
4 seek-relative seek-input
|
||||||
|
-2 seek-relative
|
||||||
|
2 read
|
||||||
|
] with-input-stream
|
||||||
|
] [
|
||||||
|
limit-exceeded?
|
||||||
|
] must-fail-with
|
||||||
|
|
||||||
|
[
|
||||||
|
"abcdefgh" <string-reader> [
|
||||||
|
4 seek-relative seek-input
|
||||||
|
2 stream-throws limit-input
|
||||||
|
-2 seek-relative seek-input
|
||||||
|
2 read
|
||||||
|
] with-input-stream
|
||||||
|
] [
|
||||||
|
limit-exceeded?
|
||||||
|
] must-fail-with
|
||||||
|
|
||||||
|
[ "ef" ] [
|
||||||
|
"abcdefgh" <string-reader> [
|
||||||
|
4 seek-relative seek-input
|
||||||
|
2 stream-throws limit-input
|
||||||
|
4 seek-absolute seek-input
|
||||||
|
2 read
|
||||||
|
] with-input-stream
|
||||||
|
] unit-test
|
||||||
|
|
||||||
|
[ "ef" ] [
|
||||||
|
"abcdefgh" <string-reader> [
|
||||||
|
4 seek-absolute seek-input
|
||||||
|
2 stream-throws limit-input
|
||||||
|
2 seek-absolute seek-input
|
||||||
|
4 seek-absolute seek-input
|
||||||
|
2 read
|
||||||
|
] with-input-stream
|
||||||
|
] unit-test
|
||||||
|
|
||||||
|
! stream-throws, pipes are duplex and not seekable
|
||||||
|
[ "as" ] [
|
||||||
|
latin1 <pipe> [ 2 stream-throws <limited-stream> ] change-in
|
||||||
|
"asdf" over stream-write dup stream-flush
|
||||||
|
2 swap stream-read
|
||||||
|
] unit-test
|
||||||
|
|
||||||
|
[
|
||||||
|
latin1 <pipe> [ 2 stream-throws <limited-stream> ] change-in
|
||||||
|
"asdf" over stream-write dup stream-flush
|
||||||
|
3 swap stream-read
|
||||||
|
] [
|
||||||
|
limit-exceeded?
|
||||||
|
] must-fail-with
|
||||||
|
|
||||||
|
! stream-eofs, pipes are duplex and not seekable
|
||||||
|
[ "as" ] [
|
||||||
|
latin1 <pipe> [ 2 stream-eofs <limited-stream> ] change-in
|
||||||
|
"asdf" over stream-write dup stream-flush
|
||||||
|
2 swap stream-read
|
||||||
|
] unit-test
|
||||||
|
|
||||||
|
[ "as" ] [
|
||||||
|
latin1 <pipe> [ 2 stream-eofs <limited-stream> ] change-in
|
||||||
|
"asdf" over stream-write dup stream-flush
|
||||||
|
3 swap stream-read
|
||||||
|
] unit-test
|
||||||
|
|
||||||
|
! test seeking on limited unseekable streams
|
||||||
|
[ "as" ] [
|
||||||
|
latin1 <pipe> [ 2 stream-eofs <limited-stream> ] change-in
|
||||||
|
"asdf" over stream-write dup stream-flush
|
||||||
|
2 swap stream-read
|
||||||
|
] unit-test
|
||||||
|
|
||||||
|
[ "as" ] [
|
||||||
|
latin1 <pipe> [ 2 stream-eofs <limited-stream> ] change-in
|
||||||
|
"asdf" over stream-write dup stream-flush
|
||||||
|
3 swap stream-read
|
||||||
|
] unit-test
|
||||||
|
|
||||||
|
[
|
||||||
|
latin1 <pipe> [ 2 stream-throws <limited-stream> ] change-in
|
||||||
|
2 seek-absolute rot in>> stream-seek
|
||||||
|
] must-fail
|
||||||
|
|
||||||
|
[
|
||||||
|
"as"
|
||||||
|
] [
|
||||||
|
latin1 <pipe> [ 2 stream-throws <limited-stream> ] change-in
|
||||||
|
"asdf" over stream-write dup stream-flush
|
||||||
|
[ 2 seek-absolute rot in>> stream-seek ] [ drop ] recover
|
||||||
|
2 swap stream-read
|
||||||
|
] unit-test
|
||||||
|
|
||||||
|
[ 7 ] [
|
||||||
|
image binary stream-throws <limited-file-reader> [
|
||||||
|
7 read drop
|
||||||
|
tell-input
|
||||||
|
] with-input-stream
|
||||||
|
] unit-test
|
||||||
|
|
||||||
|
[ 70000 ] [
|
||||||
|
image binary stream-throws <limited-file-reader> [
|
||||||
|
70000 read drop
|
||||||
|
tell-input
|
||||||
|
] with-input-stream
|
||||||
|
] unit-test
|
||||||
|
|
|
@ -2,11 +2,14 @@
|
||||||
! Copyright (C) 2009 Doug Coleman.
|
! Copyright (C) 2009 Doug Coleman.
|
||||||
! See http://factorcode.org/license.txt for BSD license.
|
! See http://factorcode.org/license.txt for BSD license.
|
||||||
USING: accessors byte-vectors combinators destructors fry io
|
USING: accessors byte-vectors combinators destructors fry io
|
||||||
io.encodings io.files io.files.info kernel math namespaces
|
io.encodings io.files io.files.info kernel locals math
|
||||||
sequences ;
|
namespaces sequences ;
|
||||||
IN: io.streams.limited
|
IN: io.streams.limited
|
||||||
|
|
||||||
TUPLE: limited-stream stream count limit mode stack ;
|
TUPLE: limited-stream
|
||||||
|
stream mode
|
||||||
|
count limit
|
||||||
|
current start stop ;
|
||||||
|
|
||||||
SINGLETONS: stream-throws stream-eofs ;
|
SINGLETONS: stream-throws stream-eofs ;
|
||||||
|
|
||||||
|
@ -51,13 +54,27 @@ M: object unlimited ( stream -- stream' )
|
||||||
: with-limited-stream ( stream limit mode quot -- )
|
: with-limited-stream ( stream limit mode quot -- )
|
||||||
[ limit ] dip call ; inline
|
[ limit ] dip call ; inline
|
||||||
|
|
||||||
ERROR: limit-exceeded ;
|
ERROR: limit-exceeded n stream ;
|
||||||
|
|
||||||
ERROR: bad-stream-mode mode ;
|
ERROR: bad-stream-mode mode ;
|
||||||
|
|
||||||
<PRIVATE
|
<PRIVATE
|
||||||
|
|
||||||
: adjust-limit ( n stream -- n' stream )
|
: adjust-current-limit ( n stream -- n' stream )
|
||||||
|
2dup [ + ] change-current
|
||||||
|
[ current>> ] [ stop>> ] bi >
|
||||||
|
[
|
||||||
|
dup mode>> {
|
||||||
|
{ stream-throws [ limit-exceeded ] }
|
||||||
|
{ stream-eofs [
|
||||||
|
dup [ current>> ] [ stop>> ] bi -
|
||||||
|
'[ _ - ] dip
|
||||||
|
] }
|
||||||
|
[ bad-stream-mode ]
|
||||||
|
} case
|
||||||
|
] when ; inline
|
||||||
|
|
||||||
|
: adjust-count-limit ( n stream -- n' stream )
|
||||||
2dup [ + ] change-count
|
2dup [ + ] change-count
|
||||||
[ count>> ] [ limit>> ] bi >
|
[ count>> ] [ limit>> ] bi >
|
||||||
[
|
[
|
||||||
|
@ -66,13 +83,29 @@ ERROR: bad-stream-mode mode ;
|
||||||
{ stream-eofs [
|
{ stream-eofs [
|
||||||
dup [ count>> ] [ limit>> ] bi -
|
dup [ count>> ] [ limit>> ] bi -
|
||||||
'[ _ - ] dip
|
'[ _ - ] dip
|
||||||
|
dup limit>> >>count
|
||||||
] }
|
] }
|
||||||
[ bad-stream-mode ]
|
[ bad-stream-mode ]
|
||||||
} case
|
} case
|
||||||
] when ; inline
|
] when ; inline
|
||||||
|
|
||||||
|
: check-count-bounds ( n stream -- n stream )
|
||||||
|
dup [ count>> ] [ limit>> ] bi >
|
||||||
|
[ limit-exceeded ] when ;
|
||||||
|
|
||||||
|
: check-current-bounds ( n stream -- n stream )
|
||||||
|
dup [ current>> ] [ start>> ] bi <
|
||||||
|
[ limit-exceeded ] when ;
|
||||||
|
|
||||||
|
: adjust-limited-read ( n stream -- n stream )
|
||||||
|
dup start>> [
|
||||||
|
check-current-bounds adjust-current-limit
|
||||||
|
] [
|
||||||
|
check-count-bounds adjust-count-limit
|
||||||
|
] if ;
|
||||||
|
|
||||||
: maybe-read ( n limited-stream quot: ( n stream -- seq/f ) -- seq/f )
|
: maybe-read ( n limited-stream quot: ( n stream -- seq/f ) -- seq/f )
|
||||||
[ adjust-limit ] dip
|
[ adjust-limited-read ] dip
|
||||||
pick 0 <= [ 3drop f ] [ [ stream>> ] dip call ] if ; inline
|
pick 0 <= [ 3drop f ] [ [ stream>> ] dip call ] if ; inline
|
||||||
|
|
||||||
PRIVATE>
|
PRIVATE>
|
||||||
|
@ -93,16 +126,35 @@ M: limited-stream stream-read-partial
|
||||||
3dup [ [ stream-read1 dup ] dip memq? ] dip
|
3dup [ [ stream-read1 dup ] dip memq? ] dip
|
||||||
swap [ drop ] [ push (read-until) ] if ;
|
swap [ drop ] [ push (read-until) ] if ;
|
||||||
|
|
||||||
|
:: limited-stream-seek ( n seek-type stream -- )
|
||||||
|
seek-type {
|
||||||
|
{ seek-absolute [ n stream (>>current) ] }
|
||||||
|
{ seek-relative [ stream [ n + ] change-current drop ] }
|
||||||
|
{ seek-end [ stream stop>> n - stream (>>current) ] }
|
||||||
|
[ bad-seek-type ]
|
||||||
|
} case ;
|
||||||
|
|
||||||
|
: >limited-seek ( stream -- stream' )
|
||||||
|
dup start>> [
|
||||||
|
dup stream-tell >>current
|
||||||
|
dup [ current>> ] [ count>> ] bi - >>start
|
||||||
|
dup [ start>> ] [ limit>> ] bi + >>stop
|
||||||
|
] unless ;
|
||||||
|
|
||||||
PRIVATE>
|
PRIVATE>
|
||||||
|
|
||||||
M: limited-stream stream-read-until
|
M: limited-stream stream-read-until
|
||||||
swap BV{ } clone (read-until) [ 2nip B{ } like ] dip ;
|
swap BV{ } clone (read-until) [ 2nip B{ } like ] dip ;
|
||||||
|
|
||||||
M: limited-stream stream-seek
|
M: limited-stream stream-tell
|
||||||
stream>> stream-seek ;
|
stream>> stream-tell ;
|
||||||
|
|
||||||
M: limited-stream dispose
|
M: limited-stream stream-seek
|
||||||
stream>> dispose ;
|
>limited-seek
|
||||||
|
[ stream>> stream-seek ]
|
||||||
|
[ limited-stream-seek ] 3bi ;
|
||||||
|
|
||||||
|
M: limited-stream dispose stream>> dispose ;
|
||||||
|
|
||||||
M: limited-stream stream-element-type
|
M: limited-stream stream-element-type
|
||||||
stream>> stream-element-type ;
|
stream>> stream-element-type ;
|
||||||
|
|
|
@ -2,7 +2,8 @@
|
||||||
! See http://factorcode.org/license.txt for BSD license.
|
! See http://factorcode.org/license.txt for BSD license.
|
||||||
USING: accessors io kernel math namespaces sequences sbufs
|
USING: accessors io kernel math namespaces sequences sbufs
|
||||||
strings generic splitting continuations destructors sequences.private
|
strings generic splitting continuations destructors sequences.private
|
||||||
io.streams.plain io.encodings math.order growable io.streams.sequence ;
|
io.streams.plain io.encodings math.order growable io.streams.sequence
|
||||||
|
io.private ;
|
||||||
IN: io.streams.string
|
IN: io.streams.string
|
||||||
|
|
||||||
! Readers
|
! Readers
|
||||||
|
@ -13,6 +14,8 @@ M: string-reader stream-read-partial stream-read ;
|
||||||
M: string-reader stream-read sequence-read ;
|
M: string-reader stream-read sequence-read ;
|
||||||
M: string-reader stream-read1 sequence-read1 ;
|
M: string-reader stream-read1 sequence-read1 ;
|
||||||
M: string-reader stream-read-until sequence-read-until ;
|
M: string-reader stream-read-until sequence-read-until ;
|
||||||
|
M: string-reader stream-tell i>> ;
|
||||||
|
M: string-reader stream-seek (stream-seek) ;
|
||||||
M: string-reader dispose drop ;
|
M: string-reader dispose drop ;
|
||||||
|
|
||||||
<PRIVATE
|
<PRIVATE
|
||||||
|
|
|
@ -486,6 +486,7 @@ tuple
|
||||||
{ "fputc" "io.streams.c" (( ch alien -- )) }
|
{ "fputc" "io.streams.c" (( ch alien -- )) }
|
||||||
{ "fwrite" "io.streams.c" (( string alien -- )) }
|
{ "fwrite" "io.streams.c" (( string alien -- )) }
|
||||||
{ "fflush" "io.streams.c" (( alien -- )) }
|
{ "fflush" "io.streams.c" (( alien -- )) }
|
||||||
|
{ "ftell" "io.streams.c" (( alien -- n )) }
|
||||||
{ "fseek" "io.streams.c" (( alien offset whence -- )) }
|
{ "fseek" "io.streams.c" (( alien offset whence -- )) }
|
||||||
{ "fclose" "io.streams.c" (( alien -- )) }
|
{ "fclose" "io.streams.c" (( alien -- )) }
|
||||||
{ "<wrapper>" "kernel" (( obj -- wrapper )) }
|
{ "<wrapper>" "kernel" (( obj -- wrapper )) }
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
USING: io.files io.streams.string io io.streams.byte-array
|
USING: io.files io.streams.string io io.streams.byte-array
|
||||||
tools.test kernel io.encodings.ascii io.encodings.utf8
|
tools.test kernel io.encodings.ascii io.encodings.utf8
|
||||||
namespaces accessors io.encodings ;
|
namespaces accessors io.encodings io.streams.limited ;
|
||||||
IN: io.streams.encodings.tests
|
IN: io.streams.encodings.tests
|
||||||
|
|
||||||
[ { } ]
|
[ { } ]
|
||||||
|
|
|
@ -50,6 +50,10 @@ M: object <decoder> f decoder boa ;
|
||||||
M: decoder stream-element-type
|
M: decoder stream-element-type
|
||||||
drop +character+ ;
|
drop +character+ ;
|
||||||
|
|
||||||
|
M: decoder stream-tell stream>> stream-tell ;
|
||||||
|
|
||||||
|
M: decoder stream-seek stream>> stream-seek ;
|
||||||
|
|
||||||
M: decoder stream-read1
|
M: decoder stream-read1
|
||||||
dup >decoder< decode-char fix-read1 ;
|
dup >decoder< decode-char fix-read1 ;
|
||||||
|
|
||||||
|
|
|
@ -86,6 +86,14 @@ HELP: stream-copy
|
||||||
{ $description "Copies the contents of one stream into another, closing both streams when done." }
|
{ $description "Copies the contents of one stream into another, closing both streams when done." }
|
||||||
$io-error ;
|
$io-error ;
|
||||||
|
|
||||||
|
HELP: stream-tell
|
||||||
|
{ $values
|
||||||
|
{ "stream" "a stream" } { "n" integer }
|
||||||
|
}
|
||||||
|
{ $description "Returns the index of the stream pointer if the stream is seekable." }
|
||||||
|
{ $notes "Stream seeking is not supported on streams that do not have a known length, e.g. TCP/IP streams." } ;
|
||||||
|
|
||||||
|
|
||||||
HELP: stream-seek
|
HELP: stream-seek
|
||||||
{ $values
|
{ $values
|
||||||
{ "n" integer } { "seek-type" "a seek singleton" } { "stream" "a stream" }
|
{ "n" integer } { "seek-type" "a seek singleton" } { "stream" "a stream" }
|
||||||
|
@ -274,8 +282,11 @@ $nl
|
||||||
}
|
}
|
||||||
"This word is only required for string output streams:"
|
"This word is only required for string output streams:"
|
||||||
{ $subsections stream-nl }
|
{ $subsections stream-nl }
|
||||||
"This word is for streams that allow seeking:"
|
"These words are for seekable streams:"
|
||||||
{ $subsections stream-seek }
|
{ $subsections
|
||||||
|
stream-tell
|
||||||
|
stream-seek
|
||||||
|
}
|
||||||
{ $see-also "io.timeouts" } ;
|
{ $see-also "io.timeouts" } ;
|
||||||
|
|
||||||
ARTICLE: "stdio-motivation" "Motivation for default streams"
|
ARTICLE: "stdio-motivation" "Motivation for default streams"
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
! Copyright (C) 2003, 2009 Slava Pestov.
|
! Copyright (C) 2003, 2009 Slava Pestov.
|
||||||
! See http://factorcode.org/license.txt for BSD license.
|
! See http://factorcode.org/license.txt for BSD license.
|
||||||
USING: hashtables generic kernel math namespaces make sequences
|
USING: accessors combinators continuations destructors kernel
|
||||||
continuations destructors assocs combinators ;
|
math namespaces sequences ;
|
||||||
IN: io
|
IN: io
|
||||||
|
|
||||||
SYMBOLS: +byte+ +character+ ;
|
SYMBOLS: +byte+ +character+ ;
|
||||||
|
@ -23,9 +23,24 @@ ERROR: bad-seek-type type ;
|
||||||
|
|
||||||
SINGLETONS: seek-absolute seek-relative seek-end ;
|
SINGLETONS: seek-absolute seek-relative seek-end ;
|
||||||
|
|
||||||
|
GENERIC: stream-tell ( stream -- n )
|
||||||
GENERIC: stream-seek ( n seek-type stream -- )
|
GENERIC: stream-seek ( n seek-type stream -- )
|
||||||
|
|
||||||
: stream-print ( str stream -- ) [ stream-write ] keep stream-nl ;
|
<PRIVATE
|
||||||
|
|
||||||
|
SLOT: i
|
||||||
|
|
||||||
|
: (stream-seek) ( n seek-type stream -- )
|
||||||
|
swap {
|
||||||
|
{ seek-absolute [ (>>i) ] }
|
||||||
|
{ seek-relative [ [ + ] change-i drop ] }
|
||||||
|
{ seek-end [ [ underlying>> length + ] [ (>>i) ] bi ] }
|
||||||
|
[ bad-seek-type ]
|
||||||
|
} case ;
|
||||||
|
|
||||||
|
PRIVATE>
|
||||||
|
|
||||||
|
: stream-print ( str stream -- ) [ stream-write ] [ stream-nl ] bi ;
|
||||||
|
|
||||||
! Default streams
|
! Default streams
|
||||||
SYMBOL: input-stream
|
SYMBOL: input-stream
|
||||||
|
@ -37,6 +52,8 @@ SYMBOL: error-stream
|
||||||
: read ( n -- seq ) input-stream get stream-read ;
|
: read ( n -- seq ) input-stream get stream-read ;
|
||||||
: read-until ( seps -- seq sep/f ) input-stream get stream-read-until ;
|
: read-until ( seps -- seq sep/f ) input-stream get stream-read-until ;
|
||||||
: read-partial ( n -- seq ) input-stream get stream-read-partial ;
|
: read-partial ( n -- seq ) input-stream get stream-read-partial ;
|
||||||
|
: tell-input ( -- n ) input-stream get stream-tell ;
|
||||||
|
: tell-output ( -- n ) output-stream get stream-tell ;
|
||||||
: seek-input ( n seek-type -- ) input-stream get stream-seek ;
|
: seek-input ( n seek-type -- ) input-stream get stream-seek ;
|
||||||
: seek-output ( n seek-type -- ) output-stream get stream-seek ;
|
: seek-output ( n seek-type -- ) output-stream get stream-seek ;
|
||||||
|
|
||||||
|
|
|
@ -29,6 +29,10 @@ io.encodings.utf8 io kernel arrays strings namespaces math ;
|
||||||
] with-byte-reader
|
] with-byte-reader
|
||||||
] unit-test
|
] unit-test
|
||||||
|
|
||||||
|
[ 0 ] [
|
||||||
|
B{ 1 2 3 4 5 6 7 8 9 10 11 12 } binary [ tell-input ] with-byte-reader
|
||||||
|
] unit-test
|
||||||
|
|
||||||
! Overly aggressive compiler optimizations
|
! Overly aggressive compiler optimizations
|
||||||
[ B{ 123 } ] [
|
[ B{ 123 } ] [
|
||||||
binary [ 123 >bignum write1 ] with-byte-writer
|
binary [ 123 >bignum write1 ] with-byte-writer
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
! Copyright (C) 2008, 2009 Daniel Ehrenberg
|
! Copyright (C) 2008, 2009 Daniel Ehrenberg
|
||||||
! See http://factorcode.org/license.txt for BSD license.
|
! See http://factorcode.org/license.txt for BSD license.
|
||||||
USING: byte-arrays byte-vectors kernel io.encodings sequences io
|
USING: accessors byte-arrays byte-vectors destructors io
|
||||||
namespaces io.encodings.private accessors sequences.private
|
io.encodings io.private io.streams.sequence kernel namespaces
|
||||||
io.streams.sequence destructors math combinators ;
|
sequences sequences.private ;
|
||||||
IN: io.streams.byte-array
|
IN: io.streams.byte-array
|
||||||
|
|
||||||
M: byte-vector stream-element-type drop +byte+ ;
|
M: byte-vector stream-element-type drop +byte+ ;
|
||||||
|
@ -24,13 +24,8 @@ M: byte-reader stream-read1 sequence-read1 ;
|
||||||
M: byte-reader stream-read-until sequence-read-until ;
|
M: byte-reader stream-read-until sequence-read-until ;
|
||||||
M: byte-reader dispose drop ;
|
M: byte-reader dispose drop ;
|
||||||
|
|
||||||
M: byte-reader stream-seek ( n seek-type stream -- )
|
M: byte-reader stream-tell i>> ;
|
||||||
swap {
|
M: byte-reader stream-seek (stream-seek) ;
|
||||||
{ seek-absolute [ (>>i) ] }
|
|
||||||
{ seek-relative [ [ + ] change-i drop ] }
|
|
||||||
{ seek-end [ [ underlying>> length + ] keep (>>i) ] }
|
|
||||||
[ bad-seek-type ]
|
|
||||||
} case ;
|
|
||||||
|
|
||||||
: <byte-reader> ( byte-array encoding -- stream )
|
: <byte-reader> ( byte-array encoding -- stream )
|
||||||
[ B{ } like 0 byte-reader boa ] dip <decoder> ;
|
[ B{ } like 0 byte-reader boa ] dip <decoder> ;
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
USING: tools.test io.files io.files.temp io io.streams.c
|
USING: tools.test io.files io.files.temp io io.streams.c
|
||||||
io.encodings.ascii strings ;
|
io.encodings.ascii strings destructors kernel ;
|
||||||
IN: io.streams.c.tests
|
IN: io.streams.c.tests
|
||||||
|
|
||||||
[ "hello world" ] [
|
[ "hello world" ] [
|
||||||
|
@ -8,3 +8,12 @@ IN: io.streams.c.tests
|
||||||
"test.txt" temp-file "rb" fopen <c-reader> stream-contents
|
"test.txt" temp-file "rb" fopen <c-reader> stream-contents
|
||||||
>string
|
>string
|
||||||
] unit-test
|
] unit-test
|
||||||
|
|
||||||
|
[ 0 ]
|
||||||
|
[ "test.txt" temp-file "rb" fopen <c-reader> [ stream-tell ] [ dispose ] bi ] unit-test
|
||||||
|
|
||||||
|
[ 3 ] [
|
||||||
|
"test.txt" temp-file "rb" fopen <c-reader>
|
||||||
|
3 over stream-read drop
|
||||||
|
[ stream-tell ] [ dispose ] bi
|
||||||
|
] unit-test
|
||||||
|
|
|
@ -13,6 +13,8 @@ TUPLE: c-stream < disposable handle ;
|
||||||
|
|
||||||
M: c-stream dispose* handle>> fclose ;
|
M: c-stream dispose* handle>> fclose ;
|
||||||
|
|
||||||
|
M: c-stream stream-tell handle>> ftell ;
|
||||||
|
|
||||||
M: c-stream stream-seek
|
M: c-stream stream-seek
|
||||||
handle>> swap {
|
handle>> swap {
|
||||||
{ seek-absolute [ 0 ] }
|
{ seek-absolute [ 0 ] }
|
||||||
|
|
11
vm/io.cpp
11
vm/io.cpp
|
@ -164,6 +164,17 @@ void factor_vm::primitive_fwrite()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void factor_vm::primitive_ftell()
|
||||||
|
{
|
||||||
|
FILE *file = (FILE *)unbox_alien();
|
||||||
|
off_t offset;
|
||||||
|
|
||||||
|
if((offset = FTELL(file)) == -1)
|
||||||
|
io_error();
|
||||||
|
|
||||||
|
box_signed_8(offset);
|
||||||
|
}
|
||||||
|
|
||||||
void factor_vm::primitive_fseek()
|
void factor_vm::primitive_fseek()
|
||||||
{
|
{
|
||||||
int whence = to_fixnum(dpop());
|
int whence = to_fixnum(dpop());
|
||||||
|
|
|
@ -23,6 +23,7 @@ typedef char symbol_char;
|
||||||
#define STRNCMP strncmp
|
#define STRNCMP strncmp
|
||||||
#define STRDUP strdup
|
#define STRDUP strdup
|
||||||
|
|
||||||
|
#define FTELL ftello
|
||||||
#define FSEEK fseeko
|
#define FSEEK fseeko
|
||||||
|
|
||||||
#define FIXNUM_FORMAT "%ld"
|
#define FIXNUM_FORMAT "%ld"
|
||||||
|
|
|
@ -19,7 +19,8 @@ typedef wchar_t vm_char;
|
||||||
#define STRNCMP wcsncmp
|
#define STRNCMP wcsncmp
|
||||||
#define STRDUP _wcsdup
|
#define STRDUP _wcsdup
|
||||||
#define MIN(a,b) ((a)>(b)?(b):(a))
|
#define MIN(a,b) ((a)>(b)?(b):(a))
|
||||||
#define FSEEK fseek
|
#define FTELL _ftelli64
|
||||||
|
#define FSEEK _fseeki64
|
||||||
|
|
||||||
#ifdef WIN64
|
#ifdef WIN64
|
||||||
#define CELL_FORMAT "%Iu"
|
#define CELL_FORMAT "%Iu"
|
||||||
|
|
|
@ -128,6 +128,7 @@ const primitive_type primitives[] = {
|
||||||
primitive_fputc,
|
primitive_fputc,
|
||||||
primitive_fwrite,
|
primitive_fwrite,
|
||||||
primitive_fflush,
|
primitive_fflush,
|
||||||
|
primitive_ftell,
|
||||||
primitive_fseek,
|
primitive_fseek,
|
||||||
primitive_fclose,
|
primitive_fclose,
|
||||||
primitive_wrapper,
|
primitive_wrapper,
|
||||||
|
@ -254,6 +255,7 @@ PRIMITIVE_FORWARD(fread)
|
||||||
PRIMITIVE_FORWARD(fputc)
|
PRIMITIVE_FORWARD(fputc)
|
||||||
PRIMITIVE_FORWARD(fwrite)
|
PRIMITIVE_FORWARD(fwrite)
|
||||||
PRIMITIVE_FORWARD(fflush)
|
PRIMITIVE_FORWARD(fflush)
|
||||||
|
PRIMITIVE_FORWARD(ftell)
|
||||||
PRIMITIVE_FORWARD(fseek)
|
PRIMITIVE_FORWARD(fseek)
|
||||||
PRIMITIVE_FORWARD(fclose)
|
PRIMITIVE_FORWARD(fclose)
|
||||||
PRIMITIVE_FORWARD(wrapper)
|
PRIMITIVE_FORWARD(wrapper)
|
||||||
|
|
|
@ -136,6 +136,7 @@ PRIMITIVE(fread);
|
||||||
PRIMITIVE(fputc);
|
PRIMITIVE(fputc);
|
||||||
PRIMITIVE(fwrite);
|
PRIMITIVE(fwrite);
|
||||||
PRIMITIVE(fflush);
|
PRIMITIVE(fflush);
|
||||||
|
PRIMITIVE(ftell);
|
||||||
PRIMITIVE(fseek);
|
PRIMITIVE(fseek);
|
||||||
PRIMITIVE(fclose);
|
PRIMITIVE(fclose);
|
||||||
PRIMITIVE(wrapper);
|
PRIMITIVE(wrapper);
|
||||||
|
|
|
@ -493,6 +493,7 @@ struct factor_vm
|
||||||
void primitive_fread();
|
void primitive_fread();
|
||||||
void primitive_fputc();
|
void primitive_fputc();
|
||||||
void primitive_fwrite();
|
void primitive_fwrite();
|
||||||
|
void primitive_ftell();
|
||||||
void primitive_fseek();
|
void primitive_fseek();
|
||||||
void primitive_fflush();
|
void primitive_fflush();
|
||||||
void primitive_fclose();
|
void primitive_fclose();
|
||||||
|
|
Loading…
Reference in New Issue