@@ -25,12 +25,19 @@ var caml_sys_fds = new Array(3);
2525//Provides: caml_sys_close
2626//Requires: caml_sys_fds
2727function caml_sys_close ( fd ) {
28- var file = caml_sys_fds [ fd ] ;
29- if ( file ) file . close ( ) ;
30- delete caml_sys_fds [ fd ] ;
28+ var x = caml_sys_fds [ fd ] ;
29+ if ( x ) {
30+ x . file . close ( ) ;
31+ delete caml_sys_fds [ fd ] ;
32+ }
3133 return 0 ;
3234}
3335
36+ //Provides: MlChanid
37+ function MlChanid ( id ) {
38+ this . id = id ;
39+ }
40+
3441//Provides: caml_sys_open
3542//Requires: caml_raise_sys_error
3643//Requires: MlFakeFd_out
@@ -39,11 +46,16 @@ function caml_sys_close(fd) {
3946//Requires: fs_node_supported
4047//Requires: caml_sys_fds
4148//Requires: caml_sys_open_for_node
49+ //Requires: MlChanid
4250function caml_sys_open_internal ( file , idx ) {
51+ var chanid ;
4352 if ( idx === undefined ) {
4453 idx = caml_sys_fds . length ;
45- }
46- caml_sys_fds [ idx ] = file ;
54+ chanid = new MlChanid ( idx ) ;
55+ } else if ( caml_sys_fds [ idx ] ) {
56+ chanid = caml_sys_fds [ idx ] . chanid ;
57+ } else chanid = new MlChanid ( idx ) ;
58+ caml_sys_fds [ idx ] = { file : file , chanid : chanid } ;
4759 return idx | 0 ;
4860}
4961function caml_sys_open ( name , flags , _perms ) {
@@ -125,41 +137,58 @@ function caml_ml_set_channel_name(chanid, name) {
125137}
126138
127139//Provides: caml_ml_channels
128- var caml_ml_channels = new Array ( ) ;
140+ //Requires: MlChanid
141+ function caml_ml_channels_state ( ) {
142+ this . map = new globalThis . WeakMap ( ) ;
143+ this . opened = new globalThis . Set ( ) ;
144+ }
145+ caml_ml_channels_state . prototype . close = function ( chanid ) {
146+ this . opened . delete ( chanid ) ;
147+ } ;
148+ caml_ml_channels_state . prototype . get = function ( chanid ) {
149+ return this . map . get ( chanid ) ;
150+ } ;
151+ caml_ml_channels_state . prototype . set = function ( chanid , val ) {
152+ if ( val . opened ) this . opened . add ( chanid ) ;
153+ return this . map . set ( chanid , val ) ;
154+ } ;
155+ caml_ml_channels_state . prototype . all = function ( ) {
156+ return this . opened . values ( ) ;
157+ } ;
158+
159+ var caml_ml_channels = new caml_ml_channels_state ( ) ;
160+
161+ //Provides: caml_ml_channel_get
162+ //Requires: caml_ml_channels
163+ function caml_ml_channel_get ( id ) {
164+ return caml_ml_channels . get ( id ) ;
165+ }
129166
130167//Provides: caml_ml_channel_redirect
131168//Requires: caml_ml_channel_get, caml_ml_channels
132169function caml_ml_channel_redirect ( captured , into ) {
133170 var to_restore = caml_ml_channel_get ( captured ) ;
134171 var new_ = caml_ml_channel_get ( into ) ;
135- caml_ml_channels [ captured ] = new_ ; // XXX
172+ caml_ml_channels . set ( captured , new_ ) ;
136173 return to_restore ;
137174}
138175
139176//Provides: caml_ml_channel_restore
140177//Requires: caml_ml_channels
141178function caml_ml_channel_restore ( captured , to_restore ) {
142- caml_ml_channels [ captured ] = to_restore ; // XXX
179+ caml_ml_channels . set ( captured , to_restore ) ;
143180 return 0 ;
144181}
145182
146- //Provides: caml_ml_channel_get
147- //Requires: caml_ml_channels
148- function caml_ml_channel_get ( id ) {
149- return caml_ml_channels [ id ] ; // XXX
150- }
151-
152183//Provides: caml_ml_out_channels_list
153184//Requires: caml_ml_channels
185+ //Requires: caml_ml_channel_get
154186function caml_ml_out_channels_list ( ) {
155187 var l = 0 ;
156- for ( var c = 0 ; c < caml_ml_channels . length ; c ++ ) {
157- if (
158- caml_ml_channels [ c ] &&
159- caml_ml_channels [ c ] . opened &&
160- caml_ml_channels [ c ] . out
161- )
162- l = [ 0 , caml_ml_channels [ c ] . fd , l ] ;
188+ var keys = caml_ml_channels . all ( ) ;
189+ for ( var k of keys ) {
190+ var chan = caml_ml_channel_get ( k ) ;
191+ if ( chan . opened && chan . out ) l = [ 0 , k , l ] ;
163192 }
164193 return l ;
165194}
@@ -169,7 +198,11 @@ function caml_ml_out_channels_list() {
169198//Requires: caml_raise_sys_error
170199//Requires: caml_sys_open
171200function caml_ml_open_descriptor_out ( fd ) {
172- var file = caml_sys_fds [ fd ] ;
201+ var fd_desc = caml_sys_fds [ fd ] ;
202+ if ( fd_desc === undefined )
203+ caml_raise_sys_error ( "fd " + fd + " doesn't exist" ) ;
204+ var file = fd_desc . file ;
205+ var chanid = fd_desc . chanid ;
173206 if ( file . flags . rdonly ) caml_raise_sys_error ( "fd " + fd + " is readonly" ) ;
174207 var buffered = file . flags . buffered !== undefined ? file . flags . buffered : 1 ;
175208 var channel = {
@@ -182,16 +215,20 @@ function caml_ml_open_descriptor_out(fd) {
182215 buffer : new Uint8Array ( 65536 ) ,
183216 buffered : buffered ,
184217 } ;
185- caml_ml_channels [ channel . fd ] = channel ;
186- return channel . fd ;
218+ caml_ml_channels . set ( chanid , channel ) ;
219+ return chanid ;
187220}
188221
189222//Provides: caml_ml_open_descriptor_in
190223//Requires: caml_ml_channels, caml_sys_fds
191224//Requires: caml_raise_sys_error
192225//Requires: caml_sys_open
193226function caml_ml_open_descriptor_in ( fd ) {
194- var file = caml_sys_fds [ fd ] ;
227+ var fd_desc = caml_sys_fds [ fd ] ;
228+ if ( fd_desc === undefined )
229+ caml_raise_sys_error ( "fd " + fd + " doesn't exist" ) ;
230+ var file = fd_desc . file ;
231+ var chanid = fd_desc . chanid ;
195232 if ( file . flags . wronly ) caml_raise_sys_error ( "fd " + fd + " is writeonly" ) ;
196233 var refill = null ;
197234 var channel = {
@@ -205,8 +242,8 @@ function caml_ml_open_descriptor_in(fd) {
205242 buffer : new Uint8Array ( 65536 ) ,
206243 refill : refill ,
207244 } ;
208- caml_ml_channels [ channel . fd ] = channel ;
209- return channel . fd ;
245+ caml_ml_channels . set ( chanid , channel ) ;
246+ return chanid ;
210247}
211248
212249//Provides: caml_ml_open_descriptor_in_with_flags
@@ -253,10 +290,12 @@ function caml_ml_is_binary_mode(chanid) {
253290//Provides: caml_ml_close_channel
254291//Requires: caml_ml_flush, caml_ml_channel_get
255292//Requires: caml_sys_close
293+ //Requires: caml_ml_channels
256294function caml_ml_close_channel ( chanid ) {
257295 var chan = caml_ml_channel_get ( chanid ) ;
258296 if ( chan . opened ) {
259297 chan . opened = false ;
298+ caml_ml_channels . close ( chanid ) ;
260299 caml_sys_close ( chan . fd ) ;
261300 chan . fd = - 1 ;
262301 chan . buffer = new Uint8Array ( 0 ) ;
0 commit comments