[m-rev.] io.m latest full diff
James Goddard
goddardjames at yahoo.com
Wed Jan 21 15:59:12 AEDT 2004
Here's the latest full diff for library/io.m's Java implementation:
Index: io.m
===================================================================
RCS file: /home/mercury1/repository/mercury/library/io.m,v
retrieving revision 1.316
diff -u -d -r1.316 io.m
--- io.m 12 Jan 2004 04:39:33 -0000 1.316
+++ io.m 21 Jan 2004 04:52:26 -0000
@@ -1168,6 +1168,11 @@
% On other systems, the file will reside in /tmp if the TMPDIR
% environment variable is not set, or in the directory specified
% by TMPDIR if it is set.
+ % For the Java implementation, the system-dependent default
+ % temporary-file directory will be used, specified by the system
+ % property java.io.tmpdir. On UNIX systems the default value of this
+ % property is typically "/tmp" or "/var/tmp"; on Microsoft Windows
+ % systems it is typically "c:\\temp".
% It is the responsibility of the program to delete the file
% when it is no longer needed.
@@ -1654,6 +1659,14 @@
ML_file_encoding_kind.ML_OS_text_encoding;
").
+:- pragma foreign_code("Java",
+"
+ static java.lang.Object ML_io_stream_db =
+ new mercury.tree234.tree234_2.empty_0();
+ static java.lang.Object ML_io_user_globals =
+ new mercury.tree234.tree234_2.empty_0();
+").
+
:- type io__stream_putback == map(io__stream_id, list(char)).
@@ -1666,6 +1679,7 @@
:- pragma foreign_type("C", io__stream, "MercuryFilePtr").
:- pragma foreign_type("il", io__stream,
"class [mercury]mercury.io__csharp_code.MR_MercuryFileStruct").
+:- pragma foreign_type("Java", io__stream, "mercury.io.MR_MercuryFileStruct").
% a unique identifier for an IO stream
:- type io__stream_id == int.
@@ -2164,6 +2178,12 @@
// in MF_Mercury_file for compatibility)
}").
+:- pragma foreign_proc("Java",
+ io__clear_err(_Stream::in, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ // XXX as for .NET above
+").
:- pred io__check_err(stream, io__res, io__state, io__state).
:- mode io__check_err(in, out, di, uo) is det.
@@ -2203,6 +2223,14 @@
RetVal = 0;
}").
+:- pragma foreign_proc("Java",
+ ferror(_Stream::in, RetVal::out, _RetStr::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"{
+ // XXX see clearerr
+ RetVal = 0;
+}").
+
:- pred io__make_err_msg(string, string, io__state, io__state).
:- mode io__make_err_msg(in, out, di, uo) is det.
@@ -2228,6 +2256,13 @@
Error = MR_io_exception;
}").
+:- pragma foreign_proc("Java",
+ io__get_system_error(Error::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"{
+ Error = MR_io_exception;
+}").
+
:- pragma export(make_err_msg(in, in, out, di, uo), "ML_make_err_msg").
:- pragma foreign_proc("C",
make_err_msg(Error::in, Msg0::in, Msg::out, IO0::di, IO::uo),
@@ -2244,6 +2279,17 @@
Msg = System.String.Concat(Msg0, Error.Message);
}").
+:- pragma foreign_proc("Java",
+ make_err_msg(Error::in, Msg0::in, Msg::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure],
+"{
+ if (Error.getMessage() != null) {
+ Msg = Msg0 + Error.getMessage();
+ } else {
+ Msg = Msg0;
+ }
+}").
+
have_win32 :- semidet_fail.
:- pragma foreign_proc("C",
@@ -2353,6 +2399,13 @@
}
}").
+:- pragma foreign_proc("Java",
+ io__stream_file_size(Stream::in, Size::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ Size = Stream.size();
+").
+
io__file_modification_time(File, Result) -->
io__file_modification_time_2(File, Status, Msg, Time),
{ Status = 1 ->
@@ -2407,6 +2460,27 @@
}
}").
+:- pragma foreign_proc("Java",
+ io__file_modification_time_2(FileName::in, Status::out, Msg::out,
+ Time::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ java.util.Date date = new java.util.Date();
+ try {
+ long time = (new java.io.File(FileName)).lastModified();
+ if (time == 0) {
+ throw new java.lang.Exception(
+ ""File not found or I/O error"");
+ }
+ date.setTime(time);
+ Msg = """";
+ Status = 1;
+ } catch (java.lang.Exception e) {
+ Msg = ""lastModified() failed: "" + e.getMessage();
+ Status = 0;
+ }
+ Time = date;
+").
%-----------------------------------------------------------------------------%
@@ -2436,6 +2510,11 @@
[will_not_call_mercury, promise_pure, thread_safe],
"SUCCESS_INDICATOR = true;"
).
+:- pragma foreign_proc("Java", file_type_implemented,
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ succeeded = true;
+").
:- pred io__file_type_2(int, string, io__res(io__file_type),
io__state, io__state).
@@ -2605,6 +2684,28 @@
}
").
+:- pragma foreign_proc("Java",
+ io__file_type_2(_FollowSymLinks::in, FileName::in,
+ Result::out, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ java.io.File file = new java.io.File(FileName);
+
+ // The Java implementation can distinguish between regular files and
+ // directories, and for everything else it just returns unknown.
+
+ if (file.isFile()) {
+ Result = new mercury.io.res_1.ok_1(new mercury.io.file_type_0(
+ mercury.io.file_type_0.regular_file));
+ } else if (file.isDirectory()) {
+ Result = new mercury.io.res_1.ok_1(new mercury.io.file_type_0(
+ mercury.io.file_type_0.directory));
+ } else {
+ Result = new mercury.io.res_1.ok_1(new mercury.io.file_type_0(
+ mercury.io.file_type_0.unknown));
+ }
+").
+
:- func file_type_character_device = file_type.
:- func file_type_block_device = file_type.
:- func file_type_fifo = file_type.
@@ -2707,6 +2808,52 @@
IO = IO0;
}").
+:- pragma foreign_proc("Java",
+ io__check_file_accessibility_2(FileName::in, AccessTypes::in,
+ Result::out, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ java.lang.String permissions = null;
+
+ if (access_types_includes_read_1_p_0(
+ (mercury.list.list_1) AccessTypes))
+ {
+ permissions = ""read"";
+ }
+
+ if (access_types_includes_write_1_p_0(
+ (mercury.list.list_1) AccessTypes))
+ {
+ if (permissions == null) {
+ permissions = ""write"";
+ } else {
+ permissions = ""read,write"";
+ }
+ }
+
+ if (access_types_includes_execute_1_p_0(
+ (mercury.list.list_1) AccessTypes))
+ {
+ if (permissions == null) {
+ permissions = ""execute"";
+ } else {
+ permissions = permissions + "",execute"";
+ }
+ }
+
+ try {
+ if (permissions != null) {
+ java.lang.System.getSecurityManager().checkPermission(
+ new java.io.FilePermission(
+ FileName, permissions));
+ }
+ Result = make_io_res_0_ok_0_f_0();
+ }
+ catch (java.lang.Exception e) {
+ Result = make_io_res_0_error_msg_1_f_0(e.getMessage());
+ }
+").
+
% The .NET CLI doesn't provide an equivalent of access(), so
% we have to try to open the file to see if it is accessible.
:- pred io__check_file_accessibility_dotnet(string::in, list(access_type)::in,
@@ -2974,6 +3121,14 @@
}
").
+:- pragma foreign_proc("Java",
+ compare_file_id_2(_Res::out, _FileId1::in, _FileId2::in),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ throw new java.lang.RuntimeException(
+ ""File IDs are not supported by Java."");
+").
+
io__file_id(FileName, Result) -->
( { have_file_ids } ->
io__file_id_2(FileName, Status, Msg, FileId),
@@ -3013,6 +3168,19 @@
#endif
}").
+:- pragma foreign_proc("Java",
+ io__file_id_2(_FileName::in, _Status::out, _Msg::out,
+ _FileId::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ // This function should never be called, since have_file_ids will
+ // fail for Java.
+ if (true) { // otherwise Java complains about unreachable stmts.
+ throw new RuntimeException(
+ ""io.file_id_2 called but not supported"");
+ }
+").
+
% Can we retrieve inode numbers on this system.
have_file_ids :- semidet_fail.
:- pragma foreign_proc("C", have_file_ids,
@@ -4211,6 +4379,20 @@
ML_io_stream_db = StreamDb;
").
+:- pragma foreign_proc("Java",
+ io__get_stream_db(StreamDb::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ StreamDb = ML_io_stream_db;
+").
+
+:- pragma foreign_proc("Java",
+ io__set_stream_db(StreamDb::in, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ ML_io_stream_db = StreamDb;
+").
+
%-----------------------------------------------------------------------------%
:- pred io__insert_stream_info(io__stream::in, stream_info::in,
@@ -4294,6 +4476,20 @@
ML_io_user_globals = Globals;
").
+:- pragma foreign_proc("Java",
+ io__get_globals(Globals::uo, _IOState0::di, _IOState::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ Globals = ML_io_user_globals;
+").
+
+:- pragma foreign_proc("Java",
+ io__set_globals(Globals::di, _IOState0::di, _IOState::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ ML_io_user_globals = Globals;
+").
+
io__progname_base(DefaultName, PrognameBase) -->
io__progname(DefaultName, Progname),
{ PrognameBase = dir__basename_det(Progname) }.
@@ -4326,6 +4522,13 @@
Id = Stream.id;
").
+:- pragma foreign_proc("Java",
+ io__get_stream_id(Stream::in) = (Id::out),
+ [will_not_call_mercury, promise_pure],
+"
+ Id = Stream.id;
+").
+
%-----------------------------------------------------------------------------%
%-----------------------------------------------------------------------------%
@@ -4615,6 +4818,659 @@
}
").
+:- pragma foreign_code("Java",
+"
+ // stdin, stdout, stderr and all text files are run through stream
+ // readers/writers, which use the default charset encoding. In other
+ // words, while strings and characters are stored internally using
+ // unicode, all files are read and written using the default system
+ // charset.
+ // Binary files are opened via RandomAccessFile, which supports seek,
+ // but not character encoding/decoding or buffering.
+
+ public static class MR_MercuryFileStruct {
+ public static int ML_next_stream_id = 0;
+ public int id;
+
+ public int line_number = 1;
+
+ public static final int INPUT = 0;
+ public static final int OUTPUT = 1;
+ private int mode;
+
+ private static final int SEEK_SET = 0;
+ private static final int SEEK_CUR = 1;
+ private static final int SEEK_END = 2;
+
+ private java.util.Stack pushback = null;
+ private java.io.InputStreamReader input = null;
+ private java.io.OutputStreamWriter output = null;
+ private java.io.RandomAccessFile randomaccess = null;
+
+ /* binary_stdin only */
+ private java.io.FileInputStream binary_input = null;
+ /* binary_stdout only */
+ private java.io.FileOutputStream binary_output = null;
+
+ int position = 0;
+ private java.lang.Object channel = null;
+
+ /*
+ ** This constructor is for text input streams.
+ */
+ public MR_MercuryFileStruct(java.io.InputStream stream) {
+ this(stream, false);
+ }
+
+ /*
+ ** This constructor is for text output streams.
+ */
+ public MR_MercuryFileStruct(java.io.OutputStream stream) {
+ this(stream, false);
+ }
+
+ /*
+ ** This constructor handles binary files (in or out) but does
+ ** not cover mercury_stdin_binary/mecury_stdout_binary.
+ */
+ public MR_MercuryFileStruct(java.lang.String file, char mode) {
+ id = ML_next_stream_id++;
+ String openstring;
+ if (mode == 'r') {
+ openstring = ""r"";
+ this.mode = INPUT;
+ pushback = new java.util.Stack();
+ } else if (mode == 'w' || mode == 'a') {
+ openstring = ""rw"";
+ this.mode = OUTPUT;
+ // There is no such mode as ""w"", which could
+ // be a problem for write-only files.
+ } else {
+ throw new RuntimeException(
+ ""Invalid file opening mode"");
+ }
+ try {
+ randomaccess = new java.io.RandomAccessFile(
+ file, openstring);
+ if (mode == 'a') {
+ seek(SEEK_END, 0);
+ }
+ } catch (java.lang.Exception e) {
+ throw new RuntimeException(e.getMessage());
+ // We can't just throw e or the Java compiler
+ // will complain about unreported exceptions.
+ }
+ }
+
+ public MR_MercuryFileStruct(java.io.InputStream stream,
+ boolean openAsBinary)
+ {
+ id = ML_next_stream_id++;
+ mode = INPUT;
+ pushback = new java.util.Stack();
+
+ if (!openAsBinary) {
+ input = new java.io.
+ InputStreamReader(stream);
+ } else {
+ /* open stdin as binary */
+ binary_input = new java.io.FileInputStream(
+ java.io.FileDescriptor.in);
+ channel = get_channel(binary_input);
+ }
+ }
+
+ public MR_MercuryFileStruct(java.io.OutputStream stream,
+ boolean openAsBinary)
+ {
+ id = ML_next_stream_id++;
+ mode = OUTPUT;
+
+ if (!openAsBinary) {
+ output = new java.io.
+ OutputStreamWriter(stream);
+ } else {
+ /* open stdout as binary */
+ binary_output = new java.io.FileOutputStream(
+ java.io.FileDescriptor.out);
+ channel = get_channel(binary_output);
+ }
+ }
+
+ /*
+ ** size():
+ ** Returns the length of a binary file. XXX Note that this
+ ** method will return -1 for mercury_stdin_binary and
+ ** the current position for mercury_stdout_binary in Java
+ ** versions < 1.4.
+ */
+ public int size() {
+ if (randomaccess != null) {
+ try {
+ return (int) randomaccess.length();
+ } catch (java.io.IOException e) {
+ return -1;
+ }
+ }
+
+ try {
+ java.lang.reflect.Method size_mth =
+ channel.getClass().
+ getMethod(""size"", null);
+ return ((Long) size_mth.invoke(channel, null)).
+ intValue();
+ } catch (java.lang.Exception e) {
+ if (binary_output != null) {
+ return position;
+ } else {
+ return -1;
+ }
+ }
+ }
+
+ /*
+ ** seek():
+ ** seek relative to start, current position or end
+ ** depending on the flag.
+ ** This function only works for binary files.
+ ** The binary versions of stdin and stdout are treated
+ ** specially. For java version 1.4, Reflection is used to
+ ** obtain and use the neccessary FileChannel object needed
+ ** to perform seeking on each.
+ ** For older versions, seeking is rather limited.
+ ** For mercury_stdin_binary, seek may be
+ ** only be done forwards from the current position and for
+ ** mercury_stdout_binary seek is not supported at all.
+ */
+ public void seek(int flag, int offset) {
+ if (channel != null) {
+ channelSeek(flag, offset);
+ return;
+ }
+
+ if (input != null || output != null) {
+ throw new java.lang.RuntimeException(
+ ""text streams are not "" +
+ ""seekable"");
+ }
+ if (binary_output != null) {
+ throw new java.lang.RuntimeException(
+ ""mercury_stdout_binary is "" +
+ ""not seekable"");
+ }
+ if (binary_input != null &&
+ (flag != SEEK_CUR || offset < 0))
+ {
+ throw new java.lang.RuntimeException(
+ ""mercury_stdin_binary may "" +
+ ""only seek forwards from "" +
+ ""the current position"");
+ }
+
+ pushback = new java.util.Stack();
+ line_number = 1;
+
+ try {
+ switch (flag) {
+ case SEEK_SET:
+ randomaccess.seek(offset);
+ break;
+ case SEEK_CUR:
+ if (randomaccess != null) {
+ randomaccess.seek(
+ randomaccess.
+ getFilePointer() +
+ offset);
+ } else {
+ binary_input.skip(offset);
+ }
+ break;
+ case SEEK_END:
+ randomaccess.seek(
+ randomaccess.length() +
+ offset);
+ break;
+ default:
+ throw new java.lang.
+ RuntimeException(
+ ""Invalid seek flag"");
+ }
+ } catch (java.lang.Exception e) {
+ throw new java.lang.RuntimeException(
+ e.getMessage());
+ }
+ }
+
+ private void channelSeek(int flag, int offset) {
+ pushback = new java.util.Stack();
+ line_number = 1;
+
+ try {
+ switch (flag) {
+ case SEEK_SET:
+ position = offset;
+ break;
+ case SEEK_CUR:
+ position = getOffset() +
+ offset;
+ break;
+ case SEEK_END:
+ position = size() + offset;
+ break;
+ default:
+ throw new java.lang.
+ RuntimeException(
+ ""Invalid seek flag"");
+ }
+
+ Class[] argTypes = {Long.TYPE};
+ java.lang.reflect.Method seek_mth =
+ channel.getClass().getMethod(
+ ""position"", argTypes);
+
+ Object[] args = {new Long(position)};
+ seek_mth.invoke(channel, args);
+ }
+ catch (java.lang.Exception e) {
+ throw new java.lang.RuntimeException(
+ e.getMessage());
+ }
+ }
+
+ /*
+ ** getOffset():
+ ** Returns the current position in a binary file.
+ */
+ public int getOffset() {
+ if (randomaccess != null) {
+ try {
+ return (int) randomaccess.
+ getFilePointer();
+ } catch (java.io.IOException e) {
+ return -1;
+ }
+ }
+
+ try {
+ java.lang.reflect.Method posn_mth =
+ channel.getClass().
+ getMethod(""position"", null);
+ return ((Long) posn_mth.invoke(channel, null)).
+ intValue();
+ } catch (java.lang.Exception e) {
+ if (binary_input != null ||
+ binary_output != null)
+ {
+ return position;
+ } else {
+ return -1;
+ }
+ }
+ }
+
+ /*
+ ** read_char():
+ ** Reads one character in from a text input file using the
+ ** default charset decoding. Returns -1 at end of file.
+ */
+ public int read_char() {
+ int c;
+ if (input == null) {
+ throw new java.lang.RuntimeException(
+ ""read_char_code may only be called"" +
+ "" on text input streams"");
+ }
+ if (pushback.empty()) {
+ try {
+ c = input.read();
+ } catch (java.io.IOException e) {
+ throw new java.lang.RuntimeException(
+ e.getMessage());
+ }
+ } else {
+ c = ((java.lang.Integer)pushback.pop()).
+ intValue();
+ }
+ if (c == '\\n') {
+ line_number++;
+ }
+
+ return c;
+ }
+
+ /*
+ ** read_byte():
+ ** Reads one byte in from a binary file.
+ ** Returns -1 at end of file.
+ */
+ public int read_byte() {
+ int c;
+ if (mode == OUTPUT) {
+ throw new java.lang.RuntimeException(
+ ""Attempted to read output stream"");
+ }
+ if (randomaccess == null && binary_input == null) {
+ throw new java.lang.RuntimeException(
+ ""read_byte_val may only be called"" +
+ "" on binary input streams"");
+ }
+ if (pushback.empty()) {
+ try {
+ if (binary_input != null) {
+ c = binary_input.read();
+ } else {
+ c = randomaccess.read();
+ }
+ } catch (java.io.IOException e) {
+ throw new java.lang.RuntimeException(
+ e.getMessage());
+ }
+ } else {
+ c = ((java.lang.Integer)pushback.pop()).
+ intValue();
+ }
+ if (c == '\\n') {
+ line_number++;
+ }
+ if (binary_input != null) {
+ position++;
+ }
+
+ return c;
+ }
+
+ /*
+ ** ungetc():
+ ** Pushes an integer, which may represent either a byte or
+ ** a character, onto the pushback stack. This stack
+ ** is the same, regardless of whether the file is text or
+ ** binary.
+ */
+ public void ungetc(int c) {
+ if (mode == OUTPUT) {
+ throw new java.lang.RuntimeException(
+ ""Attempted to unget char to output stream"");
+ }
+ if (c == '\\n') {
+ line_number--;
+ }
+
+ pushback.push(new Integer(c));
+ }
+
+ /*
+ ** put():
+ ** Write one unit to an output stream. If the file is
+ ** text, the int will hold a character. If the file is
+ ** binary, this will be a single byte. In the former case
+ ** we assume that the lower order 16 bits hold a char, in
+ ** latter we take only the lowest 8 bits for a byte.
+ */
+ public void put(int c) {
+ if (mode == INPUT) {
+ throw new java.lang.RuntimeException(
+ ""Attempted to write to input stream"");
+ }
+ if (c == '\\n') {
+ line_number++;
+ }
+ if (binary_output != null) {
+ position++;
+ }
+
+ try {
+ if (output != null) {
+ output.write(c);
+ } else if (randomaccess != null) {
+ randomaccess.write(c);
+ } else {
+ binary_output.write(c);
+ }
+ } catch (java.io.IOException e) {
+ throw new java.lang.RuntimeException(
+ e.getMessage());
+ }
+ }
+
+ /*
+ ** write():
+ ** Writes a string to a file stream. For text files, this
+ ** string is encoded as a byte stream using default
+ ** encoding. For binary files, the lower order 8 bits of
+ ** each character are written.
+ */
+ public void write(java.lang.String s) {
+ if (mode == INPUT) {
+ throw new java.lang.RuntimeException(
+ ""Attempted to write to input stream"");
+ }
+
+ try {
+ if (output != null) {
+ for (int i = 0; i < s.length(); i++) {
+ if (s.charAt(i) == '\\n') {
+ line_number++;
+ }
+ }
+ output.write(s);
+ } else {
+ for (int i = 0; i < s.length(); i++) {
+ // lower 8 bits of each
+ put((byte) s.charAt(i));
+ }
+ }
+ } catch (java.io.IOException e) {
+ throw new java.lang.RuntimeException(
+ e.getMessage());
+ }
+ }
+
+ public void flush() {
+ if (mode == INPUT) {
+ throw new java.lang.RuntimeException(
+ ""Attempted to flush input stream"");
+ }
+
+ try {
+ if (output != null) {
+ output.flush();
+ }
+ if (binary_output != null) {
+ binary_output.flush();
+ }
+ // else randomaccess is already unbuffered.
+ } catch (java.io.IOException e) {
+ throw new java.lang.RuntimeException(
+ e.getMessage());
+ }
+ }
+
+ public void close() {
+ try {
+ if (input != null) {
+ input.close();
+ }
+ if (output != null) {
+ output.close();
+ }
+ if (randomaccess != null) {
+ randomaccess.close();
+ }
+ if (binary_input != null) {
+ binary_input.close();
+ }
+ if (binary_output != null) {
+ binary_output.close();
+ }
+ } catch (java.io.IOException e) {
+ throw new java.lang.RuntimeException(
+ ""Error closing stream"");
+ }
+ }
+ } // class MR_MercuryFileStruct
+
+ // StreamPipe is a mechanism for connecting streams to those of a
+ // Runtime.exec() Process.
+
+ private static class StreamPipe extends java.lang.Thread {
+ MR_MercuryFileStruct in;
+ MR_MercuryFileStruct out;
+ boolean closeOutput = false;
+ java.lang.Exception exception = null;
+
+ StreamPipe(java.io.InputStream in, MR_MercuryFileStruct out) {
+ this.in = new MR_MercuryFileStruct(in);
+ this.out = out;
+ }
+
+ StreamPipe(MR_MercuryFileStruct in, java.io.OutputStream out) {
+ this.in = in;
+ this.out = new MR_MercuryFileStruct(out);
+ closeOutput = true;
+ }
+
+ public void run() {
+ try {
+ while (true) {
+ int b = in.read_char();
+ if (b == -1 || interrupted()) {
+ break;
+ }
+ out.put(b);
+ }
+ out.flush();
+ if (closeOutput) {
+ out.close();
+ }
+ }
+ catch (java.lang.Exception e) {
+ exception = e;
+ }
+ }
+ } // class StreamPipe
+
+ /*
+ ** get_channel():
+ ** Given some object, attempts to call getChannel() using
+ ** Reflection and returns the result, or null if getChannel() is
+ ** not available.
+ ** The reason we do this is that FileChannels were not supported
+ ** until Java v1.4, so users with older versions of Java would
+ ** not be able to compile this code if the call to getChannel were
+ ** made directly.
+ ** This way, older versions of Java will still be able to compile,
+ ** but will not support binary seeking on stdin/out properly,
+ ** since this can't be done without FileChannel.
+ */
+ static java.lang.Object/*FileChannel*/ get_channel(java.lang.Object o)
+ {
+ try {
+ // Simulate
+ // return o.getChannel();
+ // using reflection.
+ java.lang.reflect.Method getChannel_mth =
+ o.getClass().getMethod(
+ ""getChannel"", null);
+
+ return getChannel_mth.invoke(o, null);
+ }
+ catch (java.lang.Exception e) {
+ return null;
+ }
+ }
+
+ /*
+ ** get_out_channel():
+ ** Uses reflection to retrieve the FileChannel for System.out on
+ ** platforms supporting Java v1.4
+ */
+ static java.lang.Object/*FileChannel*/ get_out_channel() {
+ try {
+ java.lang.Object/*PrintStream*/ ps =
+ java.lang.System.out;
+
+ // Simulate
+ // BufferedOutputStream bos =
+ // (BufferedOutputStream) ps.out;
+ // using reflection.
+ java.lang.reflect.Field out_fld =
+ ps.getClass().getSuperclass().
+ getDeclaredField(""out"");
+ out_fld.setAccessible(true);
+ java.lang.Object/*BufferedOutputStream*/ bos =
+ out_fld.get(ps);
+
+ // Simulate
+ // FileOutputStream fs =
+ // (FileOutputStream) bos.out;
+ // using reflection.
+ java.lang.reflect.Field out_fld2 =
+ bos.getClass().getSuperclass().
+ getDeclaredField(""out"");
+ out_fld2.setAccessible(true);
+ java.lang.Object/*FileStream*/ fs = out_fld2.get(bos);
+
+ // Simulate
+ // FileChannel channel = fs.getChannel();
+ // using reflection.
+ java.lang.reflect.Method getChannel_mth =
+ fs.getClass().getMethod(
+ ""getChannel"", null);
+ java.lang.Object/*FileChannel*/ channel =
+ getChannel_mth.invoke(fs, null);
+
+ return channel;
+ } catch (java.lang.Exception e) {
+ return null;
+ }
+ }
+
+ /*
+ ** get_in_channel():
+ ** Uses reflection to retrieve the FileChannel for System.in on
+ ** platforms supporting Java v1.4
+ */
+ static java.lang.Object/*FileChannel*/ get_in_channel() {
+ try {
+ java.lang.Object/*InputStream*/ is = System.in;
+
+ // Simulate
+ // BufferedInputStream bis =
+ // (BufferedInputStream) is.in;
+ // using reflection.
+ java.lang.reflect.Field in_fld =
+ is.getClass().getSuperclass().
+ getDeclaredField(""in"");
+ in_fld.setAccessible(true);
+ java.lang.Object/*BufferedInputStream*/ bis =
+ in_fld.get(is);
+
+ // Simulate
+ // FileInputStream fs =
+ // (FileInputStream) bis.in;
+ // using reflection.
+ java.lang.reflect.Field in_fld2 =
+ bis.getClass().getSuperclass().
+ getDeclaredField(""in"");
+ in_fld2.setAccessible(true);
+ java.lang.Object/*FileStream*/ fs = in_fld2.get(bis);
+
+ // Simulate
+ // FileChannel channel = fs.getChannel();
+ // using reflection.
+ java.lang.reflect.Method getChannel_mth =
+ fs.getClass().getMethod(
+ ""getChannel"", null);
+ java.lang.Object/*FileChannel*/ channel =
+ getChannel_mth.invoke(fs, null);
+
+ return channel;
+ } catch (java.lang.Exception e) {
+ return null;
+ }
+ }
+").
+
:- pragma foreign_code("C", "
MercuryFile mercury_stdin;
@@ -4716,6 +5572,30 @@
").
+:- pragma foreign_code("Java",
+"
+static MR_MercuryFileStruct mercury_stdin =
+ new MR_MercuryFileStruct(java.lang.System.in);
+static MR_MercuryFileStruct mercury_stdout =
+ new MR_MercuryFileStruct(java.lang.System.out);
+static MR_MercuryFileStruct mercury_stderr =
+ new MR_MercuryFileStruct(java.lang.System.err);
+static MR_MercuryFileStruct mercury_stdin_binary =
+ new MR_MercuryFileStruct(java.lang.System.in, true);
+static MR_MercuryFileStruct mercury_stdout_binary =
+ new MR_MercuryFileStruct(java.lang.System.out, true);
+
+static MR_MercuryFileStruct mercury_current_text_input = mercury_stdin;
+static MR_MercuryFileStruct mercury_current_text_output = mercury_stdout;
+static MR_MercuryFileStruct mercury_current_binary_input =
+ mercury_stdin_binary;
+static MR_MercuryFileStruct mercury_current_binary_output =
+ mercury_stdout_binary;
+
+// XXX not thread-safe!
+static java.lang.Exception MR_io_exception;
+").
+
:- pragma foreign_code("C", "
@@ -4795,7 +5675,6 @@
").
-
:- pred throw_io_error(string::in) is erroneous.
:- pragma export(throw_io_error(in), "ML_throw_io_error").
throw_io_error(Message) :- throw(io_error(Message)).
@@ -4922,6 +5801,7 @@
").
+
:- pragma foreign_code("C", "
void
@@ -5399,6 +6279,35 @@
mf.putback = Byte;
}").
+:- pragma foreign_proc("Java",
+ io__read_char_code(File::in, CharCode::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure],
+"
+ CharCode = File.read_char();
+").
+
+:- pragma foreign_proc("Java",
+ io__read_byte_val(File::in, ByteVal::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure],
+"
+ ByteVal = File.read_byte();
+").
+
+:- pragma foreign_proc("Java",
+ io__putback_char(File::in, Character::in, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure],
+"
+ File.ungetc(Character);
+").
+
+:- pragma foreign_proc("Java",
+ io__putback_byte(File::in, Byte::in, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure],
+"
+ File.ungetc(Byte);
+").
+
+
/* output predicates - with output to mercury_current_text_output */
:- pragma foreign_proc("C",
@@ -5581,6 +6490,34 @@
System.out.print(Val);
").
+:- pragma foreign_proc("Java",
+ io__write_byte(Byte::in, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ mercury_current_binary_output.put((byte) Byte);
+").
+
+:- pragma foreign_proc("Java",
+ io__write_bytes(Message::in, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"{
+ mercury_current_binary_output.write(Message);
+}").
+
+:- pragma foreign_proc("Java",
+ io__flush_output(_IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ mercury_current_text_output.flush();
+").
+
+:- pragma foreign_proc("Java",
+ io__flush_binary_output(_IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ mercury_current_binary_output.flush();
+").
+
io__write_float(Float) -->
io__write_string(string__float_to_string(Float)).
@@ -5784,6 +6721,76 @@
Stream.stream.Flush();
}").
+:- pragma foreign_proc("Java",
+ io__seek_binary_2(Stream::in, Flag::in, Off::in, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ Stream.seek(Flag, Off);
+").
+
+:- pragma foreign_proc("Java",
+ io__binary_stream_offset(Stream::in, Offset::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ Offset = Stream.getOffset();
+").
+
+:- pragma foreign_proc("Java",
+ io__write_string(Stream::in, Message::in, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ Stream.write(Message);
+").
+
+:- pragma foreign_proc("Java",
+ io__write_char(Stream::in, Character::in, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ Stream.put(Character);
+").
+
+:- pragma foreign_proc("Java",
+ io__write_int(Stream::in, Val::in, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ Stream.write(java.lang.String.valueOf(Val));
+").
+
+:- pragma foreign_proc("Java",
+ io__write_float(Stream::in, Val::in, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ Stream.write(java.lang.String.valueOf(Val));
+").
+
+:- pragma foreign_proc("Java",
+ io__write_byte(Stream::in, Byte::in, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ Stream.put(Byte);
+").
+
+:- pragma foreign_proc("Java",
+ io__write_bytes(Stream::in, Message::in, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ Stream.write(Message);
+").
+
+:- pragma foreign_proc("Java",
+ io__flush_output(Stream::in, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ Stream.flush();
+").
+
+:- pragma foreign_proc("Java",
+ io__flush_binary_output(Stream::in, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ Stream.flush();
+").
+
io__write_float(Stream, Float) -->
io__write_string(Stream, string__float_to_string(Float)).
@@ -6131,6 +7138,162 @@
mercury_current_binary_output = NewStream;
").
+:- pragma foreign_proc("Java",
+ io__stdin_stream(Stream::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ Stream = mercury_stdin;
+").
+
+:- pragma foreign_proc("Java",
+ io__stdout_stream(Stream::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ Stream = mercury_stdout;
+").
+
+:- pragma foreign_proc("Java",
+ io__stderr_stream(Stream::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ Stream = mercury_stderr;
+").
+
+:- pragma foreign_proc("Java",
+ io__stdin_binary_stream(Stream::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ Stream = mercury_stdin_binary;
+").
+
+:- pragma foreign_proc("Java",
+ io__stdout_binary_stream(Stream::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, thread_safe, tabled_for_io],
+"
+ Stream = mercury_stdout_binary;
+").
+
+:- pragma foreign_proc("Java",
+ io__input_stream(Stream::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ Stream = mercury_current_text_input;
+").
+
+:- pragma foreign_proc("Java",
+ io__output_stream(Stream::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ Stream = mercury_current_text_output;
+").
+
+:- pragma foreign_proc("Java",
+ io__binary_input_stream(Stream::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ Stream = mercury_current_binary_input;
+").
+
+:- pragma foreign_proc("Java",
+ io__binary_output_stream(Stream::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ Stream = mercury_current_binary_output;
+").
+
+:- pragma foreign_proc("Java",
+ io__get_line_number(LineNum::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ LineNum = mercury_current_text_input.line_number;
+").
+
+:- pragma foreign_proc("Java",
+ io__get_line_number(Stream::in, LineNum::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"{
+ LineNum = Stream.line_number;
+}").
+
+:- pragma foreign_proc("Java",
+ io__set_line_number(LineNum::in, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ mercury_current_text_input.line_number = LineNum;
+").
+
+:- pragma foreign_proc("Java",
+ io__set_line_number(Stream::in, LineNum::in, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"{
+ Stream.line_number = LineNum;
+}").
+
+:- pragma foreign_proc("Java",
+ io__get_output_line_number(LineNum::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ LineNum = mercury_current_text_output.line_number;
+").
+
+:- pragma foreign_proc("Java",
+ io__get_output_line_number(Stream::in, LineNum::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"{
+ LineNum = Stream.line_number;
+}").
+
+:- pragma foreign_proc("Java",
+ io__set_output_line_number(LineNum::in, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ mercury_current_text_output.line_number = LineNum;
+").
+
+:- pragma foreign_proc("Java",
+ io__set_output_line_number(Stream::in, LineNum::in, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"{
+ Stream.line_number = LineNum;
+}").
+
+% io__set_input_stream(NewStream, OldStream, IO0, IO1)
+% Changes the current input stream to the stream specified.
+% Returns the previous stream.
+:- pragma foreign_proc("Java",
+ io__set_input_stream(NewStream::in, OutStream::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ OutStream = mercury_current_text_input;
+ mercury_current_text_input = NewStream;
+").
+
+:- pragma foreign_proc("Java",
+ io__set_output_stream(NewStream::in, OutStream::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ OutStream = mercury_current_text_output;
+ mercury_current_text_output = NewStream;
+").
+
+:- pragma foreign_proc("Java",
+ io__set_binary_input_stream(NewStream::in, OutStream::out,
+ _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ OutStream = mercury_current_binary_input;
+ mercury_current_binary_input = NewStream;
+").
+
+:- pragma foreign_proc("Java",
+ io__set_binary_output_stream(NewStream::in, OutStream::out,
+ _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ OutStream = mercury_current_binary_output;
+ mercury_current_binary_output = NewStream;
+").
+
/* stream open/close predicates */
% io__do_open_binary(File, Mode, ResultCode, StreamId, Stream, IO0, IO):
@@ -6203,6 +7366,55 @@
}
").
+:- pragma foreign_proc("Java",
+ io__do_open_text(FileName::in, Mode::in, ResultCode::out,
+ StreamId::out, Stream::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ try {
+ if (Mode.charAt(0) == 'r') {
+ Stream = new MR_MercuryFileStruct(
+ new java.io.FileInputStream(FileName));
+ } else if (Mode.charAt(0) == 'w') {
+ Stream = new MR_MercuryFileStruct(
+ new java.io.FileOutputStream(
+ FileName));
+ } else if (Mode.charAt(0) == 'a') {
+ Stream = new MR_MercuryFileStruct(
+ new java.io.FileOutputStream(
+ FileName, true));
+ } else {
+ throw new java.lang.RuntimeException(
+ ""io__do_open_text: Invalid open mode""
+ + "" \\"""" + Mode + ""\\"""");
+ }
+ StreamId = Stream.id;
+ ResultCode = 0;
+ } catch (java.lang.Exception e) {
+ MR_io_exception = e;
+ Stream = null;
+ StreamId = -1;
+ ResultCode = -1;
+ }
+").
+
+:- pragma foreign_proc("Java",
+ io__do_open_binary(FileName::in, Mode::in, ResultCode::out,
+ StreamId::out, Stream::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ try {
+ Stream = new MR_MercuryFileStruct(FileName, Mode.charAt(0));
+ StreamId = Stream.id;
+ ResultCode = 0;
+ } catch (java.lang.Exception e) {
+ MR_io_exception = e;
+ Stream = null;
+ StreamId = -1;
+ ResultCode = -1;
+ }
+").
+
io__close_input(Stream) -->
io__maybe_delete_stream_info(Stream),
io__close_stream(Stream).
@@ -6236,6 +7448,13 @@
mercury_close(Stream);
").
+:- pragma foreign_proc("Java",
+ io__close_stream(Stream::in, _IO0::di, _IO::uo),
+ [may_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ Stream.close();
+").
+
/* miscellaneous predicates */
:- pragma foreign_proc("C",
@@ -6438,6 +7657,109 @@
}
").
+:- pragma foreign_proc("Java",
+ io__progname(_Default::in, PrognameOut::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ PrognameOut = mercury.runtime.JavaInternal.progname;
+").
+
+:- pragma foreign_proc("Java",
+ io__get_exit_status(ExitStatus::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ ExitStatus = mercury.runtime.JavaInternal.exit_status;
+").
+
+:- pragma foreign_proc("Java",
+ io__set_exit_status(ExitStatus::in, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ mercury.runtime.JavaInternal.exit_status = ExitStatus;
+").
+
+io__command_line_arguments(Args, IO, IO) :-
+ build_command_line_args(0, Args).
+
+:- pred build_command_line_args(int, list(string)).
+:- mode build_command_line_args(in, out) is det.
+
+build_command_line_args(ArgNumber, Args) :-
+ ( command_line_argument(ArgNumber, Arg) ->
+ Args = [Arg|MoreArgs],
+ build_command_line_args(ArgNumber + 1, MoreArgs)
+ ;
+ Args = []
+ ).
+
+:- pred command_line_argument(int, string).
+:- mode command_line_argument(in, out) is semidet.
+
+ % XXX This predicate is currently only used by the Java implementation,
+ % but to prevent compilation warnings for (eg) the C implementation,
+ % some definition needs to be present.
+command_line_argument(_, "") :-
+ semidet_fail.
+
+:- pragma foreign_proc("Java",
+ command_line_argument(ArgNum::in, Arg::out),
+ [will_not_call_mercury, promise_pure, thread_safe],
+"
+ String[] arg_vector = mercury.runtime.JavaInternal.args;
+
+ if (ArgNum < arg_vector.length && ArgNum >= 0) {
+ Arg = arg_vector[ArgNum];
+ succeeded = true;
+ } else {
+ Arg = null;
+ succeeded = false;
+ }
+").
+
+:- pragma foreign_proc("Java",
+ io__call_system_code(Command::in, Status::out, Msg::out,
+ _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io],
+"
+ try {
+ java.lang.Process process = java.lang.Runtime.getRuntime().
+ exec(Command);
+
+ StreamPipe stdin = new StreamPipe(mercury_stdin,
+ process.getOutputStream());
+ StreamPipe stdout = new StreamPipe(process.getInputStream(),
+ mercury_stdout);
+ StreamPipe stderr = new StreamPipe(process.getErrorStream(),
+ mercury_stderr);
+ stdin.start();
+ stdout.start();
+ stderr.start();
+
+ Status = process.waitFor();
+ Msg = null;
+
+ // The StreamPipes are killed off after the Process is
+ // finished, so as not to waste CPU cycles with pointless
+ // threads.
+ stdin.interrupt();
+ stdout.interrupt();
+ stderr.interrupt();
+
+ if (stdin.exception != null) {
+ throw stdin.exception;
+ }
+ if (stdout.exception != null) {
+ throw stdout.exception;
+ }
+ if (stderr.exception != null) {
+ throw stderr.exception;
+ }
+ } catch (java.lang.Exception e) {
+ Status = 127;
+ Msg = e.getMessage();
+ }
+").
+
/*---------------------------------------------------------------------------*/
/* io__getenv and io__setenv */
@@ -6464,6 +7786,29 @@
SUCCESS_INDICATOR = (Value != null);
}").
+:- pragma foreign_proc("Java",
+ io__getenv(Var::in, Value::out),
+ [will_not_call_mercury, tabled_for_io],
+"
+ // Note that this approach only works for environmental variables that
+ // are recognized by Java and hava a special format.
+ // (eg os.name, user.timezone etc)
+ // To add custom environmental variables, they must be set at the
+ // command line with java's -D option
+ // (ie java -DENV_VARIABLE_NAME=$ENV_VARIABLE_NAME ClassName)
+ // XXX Perhaps a better approach would be to determine the OS at
+ // runtime and then Runtime.exec() the equivalent of 'env'?
+
+ try {
+ Value = java.lang.System.getProperty(Var);
+ succeeded = (Value != null);
+ } catch (java.lang.Exception e) {
+ Value = null;
+ succeeded = false;
+ }
+").
+
+
io__setenv(Var, Value) :-
impure io__putenv(Var ++ "=" ++ Value).
@@ -6497,6 +7842,33 @@
SUCCESS_INDICATOR = (mercury.runtime.PInvoke._putenv(VarAndValue) == 0);
").
+:- pragma foreign_proc("Java",
+ io__setenv(Var::in, Value::in),
+ [will_not_call_mercury, tabled_for_io],
+"
+ // XXX see io__getenv/2
+
+ try {
+ Value = java.lang.System.setProperty(Var, Value);
+ succeeded = true;
+ } catch (java.lang.Exception e) {
+ succeeded = false;
+ }
+").
+
+:- pragma foreign_proc("Java",
+ io__putenv(VarAndValue::in),
+ [will_not_call_mercury, tabled_for_io],
+"
+ // This procedure should never be called, as io__setenv/2 has been
+ // implemented directly for Java.
+ // This implementation is included only to suppress warnings.
+
+ throw new RuntimeException(
+ ""io__putenv/1 not implemented for Java: "" +
+ VarAndValue);
+").
+
/*---------------------------------------------------------------------------*/
io__tmpnam(Name) -->
@@ -6675,6 +8047,60 @@
}
}").
+% For the Java implementation, io__make_temp/3 is overwritten directly, since
+% Java is capable of locating the default temp directory itself.
+
+:- pragma foreign_proc("Java",
+ io__do_make_temp(_Dir::in, _Prefix::in, _Sep::in, _FileName::out,
+ _Error::out, _ErrorMessage::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ // this function should never be called.
+
+ throw new RuntimeException(""io__do_make_temp not implemented"");
+").
+
+:- pragma foreign_proc("Java",
+ io__make_temp(FileName::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ try {
+ java.io.File tmpdir = new java.io.File(
+ java.lang.System.getProperty(
+ ""java.io.tmpdir""));
+ FileName = java.io.File.createTempFile(""mtmp"", null, tmpdir).
+ getName();
+ } catch (java.lang.Exception e) {
+ throw new RuntimeException(e.getMessage());
+ // This is done instead of just 'throw e' because otherwise
+ // the java compiler complains about unreported exceptions.
+ }
+").
+
+:- pragma foreign_proc("Java",
+ io__make_temp(Dir::in, Prefix::in, FileName::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ try {
+ if (Prefix.length() < 3) {
+ // File.createTempFile() requires a Prefix which is
+ // at least 3 characters long.
+ Prefix = Prefix + ""tmp"";
+ } else if (Prefix.length() > 5) {
+ // The documentation for io__make_temp says that
+ // we should only use the first five characters
+ // of Prefix.
+ Prefix = Prefix.substring(0, 5);
+ }
+ FileName = java.io.File.createTempFile(Prefix, null,
+ new java.io.File(Dir)).getName();
+ } catch (java.lang.Exception e) {
+ throw new RuntimeException(e.getMessage());
+ // This is done instead of just 'throw e' because otherwise
+ // the java compiler complains about unreported exceptions.
+ }
+").
+
/*---------------------------------------------------------------------------*/
:- pragma foreign_decl("C", "
@@ -6831,6 +8257,27 @@
}
}").
+:- pragma foreign_proc("Java",
+ io__remove_file_2(FileName::in, RetVal::out, RetStr::out,
+ _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ try {
+ java.io.File file = new java.io.File(FileName);
+
+ if (file.delete()) {
+ RetVal = 0;
+ RetStr = """";
+ } else {
+ RetVal = -1;
+ RetStr = ""remove_file failed"";
+ }
+ } catch (java.lang.Exception e) {
+ RetVal = -1;
+ RetStr = e.getMessage();
+ }
+").
+
io__rename_file(OldFileName, NewFileName, Result, IO0, IO) :-
io__rename_file_2(OldFileName, NewFileName, Res, ResString, IO0, IO),
( Res \= 0 ->
@@ -6874,6 +8321,32 @@
}
}").
+:- pragma foreign_proc("Java",
+ io__rename_file_2(OldFileName::in, NewFileName::in, RetVal::out,
+ RetStr::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ try {
+ java.io.File file = new java.io.File(OldFileName);
+
+ if (file.exists()) {
+ if (file.renameTo(new java.io.File(NewFileName))) {
+ RetVal = 0;
+ RetStr = """";
+ } else {
+ RetVal = -1;
+ RetStr = ""rename_file failed"";
+ }
+ } else {
+ RetVal = -1;
+ RetStr = ""rename failed: No such file or directory"";
+ }
+ } catch (java.lang.Exception e) {
+ RetVal = -1;
+ RetStr = e.getMessage();
+ }
+").
+
io__have_symlinks :- semidet_fail.
:- pragma foreign_proc("C", io__have_symlinks,
@@ -6984,6 +8457,30 @@
MR_update_io(IO0, IO);
}").
+% Since io__have_symlinks will fail for Java, these procedures should never be
+% called:
+
+:- pragma foreign_proc("Java",
+ io__make_symlink_2(_FileName::in, _LinkFileName::in,
+ _Status::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ if (true) {
+ throw new java.lang.RuntimeException(
+ ""io__make_symlink_2 not implemented"");
+ }
+").
+
+:- pragma foreign_proc("Java",
+ io__read_symlink_2(_FileName::in, _TargetFileName::out,
+ _Status::out, _Error::out, _IO0::di, _IO::uo),
+ [will_not_call_mercury, promise_pure, tabled_for_io, thread_safe],
+"
+ if (true) {
+ throw new java.lang.RuntimeException(
+ ""io__read_symlink_2 not implemented"");
+ }
+").
/*---------------------------------------------------------------------------*/
--------------------------------------------------------------------------
mercury-reviews mailing list
post: mercury-reviews at cs.mu.oz.au
administrative address: owner-mercury-reviews at cs.mu.oz.au
unsubscribe: Address: mercury-reviews-request at cs.mu.oz.au Message: unsubscribe
subscribe: Address: mercury-reviews-request at cs.mu.oz.au Message: subscribe
--------------------------------------------------------------------------
More information about the reviews
mailing list