Skip to content

Commit ff187c2

Browse files
authored
Make Pipes closeable. (#78)
1 parent 2588faa commit ff187c2

File tree

4 files changed

+61
-17
lines changed

4 files changed

+61
-17
lines changed

src/file.toit

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ DIRECTORY-SYMBOLIC-LINK ::= 7
6767
An open file with a current position. Corresponds in many ways to a file
6868
descriptor in Posix.
6969
*/
70-
class Stream extends Object with io.InMixin io.OutMixin implements old-reader.Reader:
70+
class Stream extends Object with io.CloseableInMixin io.CloseableOutMixin implements old-reader.Reader:
7171
fd_ := ?
7272

7373
constructor.internal_ .fd_:
@@ -148,6 +148,12 @@ class Stream extends Object with io.InMixin io.OutMixin implements old-reader.Re
148148
try-write_ data/io.Data from/int to/int -> int:
149149
return write-to-descriptor_ fd_ data from to
150150

151+
close-reader_ -> none:
152+
close
153+
154+
close-writer_ -> none:
155+
close
156+
151157
close -> none:
152158
close_ fd_
153159

src/pipe.toit

Lines changed: 47 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -53,14 +53,38 @@ get-numbered-pipe fd/int:
5353
else:
5454
return OpenPipe.from-std_ (fd-to-pipe_ pipe-resource-group_ fd)
5555

56-
class OpenPipe extends Object with io.InMixin io.OutMixin implements old-reader.Reader:
56+
class OpenPipeReader_ extends io.CloseableReader:
57+
pipe_/OpenPipe
58+
59+
constructor .pipe_:
60+
61+
read_ -> ByteArray?:
62+
return pipe_.read_
63+
64+
close_ -> none:
65+
pipe_.close
66+
67+
class OpenPipeWriter extends io.CloseableWriter:
68+
pipe_/OpenPipe
69+
70+
constructor .pipe_:
71+
72+
try-write_ data/io.Data from/int to/int -> int:
73+
return pipe_.try-write_ data from to
74+
75+
close_ -> none:
76+
pipe_.close
77+
78+
class OpenPipe implements old-reader.Reader:
5779
resource_ := ?
5880
state_ := ?
5981
pid := null
6082
child-process-name_ /string?
6183
input_ /int := UNKNOWN-DIRECTION_
6284

6385
fd := -1 // Other end of descriptor, for child process.
86+
in_ /OpenPipeReader_? := null
87+
out_ /OpenPipeWriter? := null
6488

6589
constructor input/bool --child-process-name="child process":
6690
group := pipe-resource-group_
@@ -70,11 +94,29 @@ class OpenPipe extends Object with io.InMixin io.OutMixin implements old-reader.
7094
resource_ = pipe-pair[0]
7195
fd = pipe-pair[1]
7296
state_ = monitor.ResourceState_ pipe-resource-group_ resource_
97+
if input:
98+
in_ = null
99+
out_ = OpenPipeWriter this
100+
else:
101+
in_ = OpenPipeReader_ this
102+
out_ = null
73103

74104
constructor.from-std_ .resource_:
75105
group := pipe-resource-group_
76106
child-process-name_ = null
77107
state_ = monitor.ResourceState_ pipe-resource-group_ resource_
108+
in_ = OpenPipeReader_ this
109+
out_ = OpenPipeWriter this
110+
111+
in -> io.CloseableReader:
112+
if not in_:
113+
throw "use of output pipe as input"
114+
return in_
115+
116+
out -> io.CloseableWriter:
117+
if not out_:
118+
throw "use of input pipe as output"
119+
return out_
78120

79121
/**
80122
Deprecated. Use 'read' on $in instead.
@@ -83,8 +125,6 @@ class OpenPipe extends Object with io.InMixin io.OutMixin implements old-reader.
83125
return in.read
84126

85127
read_ -> ByteArray?:
86-
if input_ == PARENT-TO-CHILD_:
87-
throw "read from an output pipe"
88128
while true:
89129
state_.wait-for-state READ-EVENT_ | CLOSE-EVENT_
90130
result := read-from-pipe_ resource_
@@ -104,16 +144,14 @@ class OpenPipe extends Object with io.InMixin io.OutMixin implements old-reader.
104144
return try-write_ x from to
105145

106146
try-write_ data/io.Data from/int to/int -> int:
107-
if input_ == CHILD-TO-PARENT_:
108-
throw "write to an input pipe"
109147
if from == to: return 0
110148
state_.wait-for-state WRITE-EVENT_ | ERROR-EVENT_
111149
bytes-written := write-to-pipe_ resource_ data from to
112150
if bytes-written == 0: state_.clear-state WRITE-EVENT_
113151
return bytes-written
114152

115153
close:
116-
close_ resource_
154+
close-resource_ resource_
117155
if state_:
118156
state_.dispose
119157
state_ = null
@@ -158,10 +196,10 @@ write-to-pipe_ pipe data/io.Data from to:
158196
read-from-pipe_ pipe:
159197
#primitive.pipe.read
160198

161-
close_ pipe:
162-
return close_ pipe pipe-resource-group_
199+
close-resource_ pipe:
200+
return close-resource_ pipe pipe-resource-group_
163201

164-
close_ pipe resource-group:
202+
close-resource_ pipe resource-group:
165203
#primitive.pipe.close
166204

167205
/// Use the stdin/stdout/stderr that the parent Toit process has.

tests/file_test.toit

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ main:
6767

6868
try:
6969
test-out.out.write test-contents
70-
test-out.close
70+
test-out.out.close
7171

7272
10000.repeat:
7373
file.read-content filename
@@ -83,7 +83,7 @@ main:
8383

8484
test-out = file.Stream.for-write filename
8585
try:
86-
test-out.close
86+
test-out.out.close
8787
expect-equals
8888
ByteArray 0
8989
file.read-content filename
@@ -98,7 +98,7 @@ main:
9898
from := 5
9999
to := 7
100100
test-out.out.write test-contents from to
101-
test-out.close
101+
test-out.out.close
102102

103103
read-back := (file.read-content filename).to-string
104104

@@ -150,7 +150,7 @@ main:
150150

151151
test-out = file.Stream filename file.CREAT | file.WRONLY 0x1ff
152152
test-out.out.write test-contents
153-
test-out.close
153+
test-out.out.close
154154

155155
expect-equals test-contents.size (file.size filename)
156156
chdir ".."
@@ -189,7 +189,7 @@ test-recursive test-dir:
189189
paths.do:
190190
stream := file.Stream.for-write it
191191
stream.out.write it
192-
stream.close
192+
stream.out.close
193193

194194
paths.do:
195195
expect (file.is-file it)

tests/pipe_test_slow.toit

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -168,7 +168,7 @@ main args:
168168
tar-exit-code := (platform == PLATFORM-LINUX) ? 2 : 1
169169
expect-error "tar: exited with status $tar-exit-code":
170170
p := pipe.to "tar" "-xvf" "-" "foo.txt"
171-
p.close // Close without sending a valid tar file.
171+
p.out.close // Close without sending a valid tar file.
172172
173173
task:: long-running-sleep
174174

@@ -201,7 +201,7 @@ pipe-large-file:
201201
o := pipe.to [md5sum]
202202
for i := 0; i < 100; i++:
203203
o.out.write buffer
204-
o.close
204+
o.out.close
205205

206206
write-closed-stdin-exception:
207207
if file.is-file "/usr/bin/true":

0 commit comments

Comments
 (0)