


## posix-text-base-io.pkg
# Compiled by:
# src/lib/std/src/standard-core.sublib# This implements the UNIX version of the
# OS specific text primitive IO package.
# It is implemented by a trivial translation of
# the binary operations (see posix-binary-base-io.pkg).
stipulate
package string = string_guts; # string_guts is from src/lib/std/src/string-guts.pkg package int = int_guts; # int_guts is from src/lib/std/src/bind-int-32.pkg package file_position = file_position_guts; # file_position_guts is from src/lib/std/src/bind-position-31.pkg package psx = posix_1003_1b; # posix_1003_1b is from src/lib/std/src/posix-1003.1b/posix-1003-1b.pkg #
package binary_base_io = posix_binary_base_io; # posix_binary_base_io is from src/lib/std/src/posix/posix-binary-base-io.pkgherein
package posix_text_base_io
: (weak)
api {
include Winix_Base_Io; # Winix_Base_Io is from src/lib/std/src/io/winix-base-io.api stdin: Void -> base_io::Reader;
stdout: Void -> base_io::Writer;
stderr: Void -> base_io::Writer;
string_reader: String -> base_io::Reader;
} {
package base_io = text_base_io; # text_base_io is from src/lib/std/src/io/text-base-io.pkg File_Descriptor = psx::File_Descriptor;
buffer_size_b = 4096;
make_reader = psx::make_text_reader; # make_text_reader def in src/lib/std/src/posix-1003.1b/posix-io.pkg make_writer = psx::make_text_writer; # make_text_writer def in src/lib/std/src/posix-1003.1b/posix-io.pkg fun announce s x y
=
{
# print "Posix: "; print (s: String); print "\n";
x y;
};
fun open_for_read name
=
make_reader
{ fd => announce "openf" psx::openf (name, psx::O_RDONLY, psx::o::flags []),
name,
blocking_mode => TRUE
};
standard_mode
=
psx::s::flags
[ # mode 0666
psx::s::irusr, psx::s::iwusr,
psx::s::irgrp, psx::s::iwgrp,
psx::s::iroth, psx::s::iwoth
];
# createf def in src/lib/std/src/posix-1003.1b/posix-file.pkg fun create_file (name, mode, flags)
=
announce "createf" psx::createf (name, mode, flags, standard_mode);
fun open_for_write name
=
make_writer
{ fd => create_file (name, psx::O_WRONLY, psx::o::trunc),
name,
blocking_mode => TRUE,
append_mode => FALSE,
chunk_size => buffer_size_b
};
fun open_for_append name
=
make_writer
{ fd => create_file (name, psx::O_WRONLY, psx::o::append),
name,
blocking_mode => TRUE,
append_mode => TRUE,
chunk_size => buffer_size_b
};
fun stdin ()
=
make_reader
{
fd => psx::stdin,
name => "<stdin>",
blocking_mode => TRUE # Bug! Should check! XXX BUGGO FIXME
};
fun stdout ()
=
make_writer
{
fd => psx::stdout,
name => "<stdout>",
blocking_mode => TRUE, # Bug! Should check! XXX BUGGO FIXME
append_mode => FALSE, # Bug! Should check! XXX BUGGO FIXME
chunk_size => buffer_size_b
};
fun stderr ()
=
make_writer
{
fd => psx::stderr,
name => "<stderr>",
blocking_mode => TRUE, # Bug! Should check! XXX BUGGO FIXME
append_mode => FALSE, # Bug! Should check! XXX BUGGO FIXME
chunk_size => buffer_size_b
};
fun string_reader src
=
{
pos = REF 0;
closed = REF FALSE;
fun check_closed ()
=
if *closed raise exception io_exceptions::CLOSED_IO_STREAM; fi;
len = string::length src;
plen = file_position::from_int len;
fun avail ()
=
len - *pos;
fun read_ro n
=
{ p = *pos;
m = int::min (n, len-p);
check_closed ();
pos := p+m;
string::substring (src, p, m); # Could use unchecked operations here.
};
fun read_rw asl
=
{ p = *pos;
my (buf, i, n)
=
rw_vector_slice_of_chars::base asl;
m = int::min (n, len-p);
check_closed ();
pos := p+m;
rw_vector_slice_of_chars::copy_vec
{ from => vector_slice_of_chars::make_slice (src, p, THE m),
to => buf,
di => i
};
m;
};
fun get_position ()
=
{ check_closed();
file_position::from_int *pos;
};
fun set_position p
=
{ check_closed ();
if (p < 0
or p > plen
)
raise exception SUBSCRIPT;
else
pos := file_position::to_int p;
fi;
};
base_io::READER
{
name => "<string>",
chunk_size => len,
read_vector => THE (read_ro),
read_rw_vector => THE (read_rw),
read_vector_nonblocking => THE (THE o read_ro),
read_rw_vector_nonblocking => THE (THE o read_rw),
block => THE (check_closed),
can_read => THE (fn () = { check_closed(); TRUE;}),
avail => THE o avail,
get_position => THE get_position,
set_position => THE set_position,
end_position => THE (fn () = { check_closed(); plen;}),
verify_position => THE get_position,
close => fn () = closed := TRUE,
io_descriptor => NULL
};
};
}; # posix_text_base_io
end;


