internal static IO flush_before_seek(IO fptr) { if ((fptr.mode & FMODE_WBUF) > 0) { io_fflush(GetWriteFile(fptr), fptr); } return fptr; }
internal static String rb_io_getline_fast(Frame caller, IO file, char rs) { StringBuilder builder = new StringBuilder(); while (!file.EndOfStream(caller)) { READ_CHECK(caller, file.f, file); //TRAP_BEG(); int c = file.Read(caller); //TRAP_END(); if (c == IO.EOF) break; builder.Append((char)c); if ((char)c == rs) break; } if (builder.Length > 0) { file.oflineno++; lineno_global.value = file.oflineno; String line = new String(builder.ToString()); line.Tainted = true; return line; } else return null; }
internal static void READ_CHECK(Frame caller, Stream fp, IO fptr) { if (!READ_DATA_PENDING(fp)) { //rb_thread_wait_fd(fileno(fp)); rb_io_check_closed(caller, fptr); } }
internal static void rb_io_check_closed(Frame caller, IO fptr) { rb_io_check_initialized(caller, fptr); if (fptr.f == null && fptr.f2 == null) throw new IOError("closed stream").raise(caller); }
internal static void rb_io_check_readable(Frame caller, IO fptr) { rb_io_check_closed(caller, fptr); if ((fptr.mode & FMODE_READABLE) == 0) throw new IOError("not opened for reading").raise(caller); fptr.mode |= FMODE_RBUF; }
internal static long io_seek(IO fptr, long pos, int whence) { fptr = flush_before_seek(fptr); switch (whence) { case SEEK_CUR: return fptr.f.Seek(pos, SeekOrigin.Current); case SEEK_END: return fptr.f.Seek(pos, SeekOrigin.End); case SEEK_SET: default: return fptr.f.Seek(pos, SeekOrigin.Begin); } }
internal static IO prep_stdio(Stream f, int mode, Class klass) { IO io = new IO(klass); io.Init(f, mode); return io; }
internal static object rb_open_file(IO io, Frame caller, Array rest) { Class.rb_scan_args(caller, rest, 1, 2, false); object vmode = null, perm = null; if (rest.Count > 1) vmode = rest[1]; if (rest.Count > 2) perm = rest[2]; string fname = String.SafeStringValue(rest[0], caller); if (vmode is int || perm != null) { int flags; if (vmode is int) flags = (int)vmode; else flags = IO.rb_io_mode_modenum(caller, String.SafeStringValue(vmode, caller)); // TODO: fmode / perm not used //int fmode = (perm == null) ? 438 /*0666*/ : Integer.rb_num2long(perm); io.Init(fname, IO.modenumToFileMode(flags), IO.modenumToFileAccess(flags), IO.rb_io_modenum_flags(flags)); } else { string mode = (vmode == null) ? "r" : String.StringValue(vmode, caller); int flags = IO.rb_io_mode_modenum(caller, mode); io.Init(fname, IO.modenumToFileMode(flags), IO.modenumToFileAccess(flags), IO.rb_io_mode_flags(caller, mode)); } return io; }
internal static Stream GetWriteFile(IO fptr) { return ((fptr.f2 != null) ? fptr.f2 : fptr.f); }
internal static void rb_io_fptr_cleanup(IO fptr, bool noraise) { if (fptr.finalize != null) fptr.finalize.Invoke(fptr, noraise); else fptr_finalize(fptr, noraise); }
internal static void rb_io_fptr_finalize(IO fptr) { if (fptr == null) return; if (fptr._path != null) { fptr._path = null; } if (fptr.f == null && fptr.f2 == null) return; if (fptr.f.Equals(System.Console.OpenStandardInput()) || fptr.f.Equals(System.Console.OpenStandardOutput()) || fptr.f.Equals(System.Console.OpenStandardError())) return; rb_io_fptr_cleanup(fptr, true); }
internal static bool swallow(Frame caller, IO io, int term) { int c; do { c = io.Peek(caller); if (c != term) return true; //TRAPBEG; io.Read(caller); //TRAPEND; } while (c != -1); return false; }
internal static int rb_io_seek(Frame caller, IO io, int offset, int whence) { IO fptr = GetOpenFile(caller, io); try { IO.io_seek(fptr, offset, whence); } catch (System.Exception e) { throw SystemCallError.rb_sys_fail(fptr._path, e, caller).raise(caller); } return 0; }
internal static string rb_io_mode_string(IO fptr) { switch (fptr.mode & FMODE_READWRITE) { case FMODE_READABLE: default: return "r"; case FMODE_WRITABLE: return "w"; case FMODE_READWRITE: return "r+"; } }
internal static void io_fflush(Stream f, IO fptr) { //if (!rb_thread_fd_writable(fileno(f))) //{ // rb_io_check_closed(fptr); //} for (; ; ) { f.Flush(); if (f.Position >= f.Length) break; //if (!rb_io_wait_writable(fileno(f))) // throw SystemCallError.rb_sys_fail(fptr.path, null, null).raise(caller); } fptr.mode &= ~FMODE_WBUF; }
private static void fptr_finalize(IO fptr, bool noraise) { throw new System.NotImplementedException("fptr_finalize"); //int n1 = 0, n2 = 0, f1, f2 = -1; //if (fptr->f2) //{ // f2 = fileno(fptr->f2); // while (n2 = 0 && fflush(fptr->f2) < 0) // { // n2 = errno; // if (!rb_io_wait_writable(f2)) // { // break; // } // if (!fptr->f2) break; // } // if (fclose(fptr->f2) < 0 && n2 == 0) // { // n2 = errno; // } // fptr->f2 = 0; //} //if (fptr->f) //{ // f1 = fileno(fptr->f); // if ((f2 == -1) && (fptr->mode & FMODE_WBUF)) // { // while (n1 = 0 && fflush(fptr->f) < 0) // { // n1 = errno; // if (!rb_io_wait_writable(f1)) break; // if (!fptr->f) break; // } // } // if (fclose(fptr->f) < 0 && n1 == 0) // { // n1 = errno; // } // fptr->f = 0; // if (n1 == EBADF && f1 == f2) // { // n1 = 0; // } //} //if (!noraise && (n1 || n2)) //{ // errno = (n1 ? n1 : n2); // rb_sys_fail(fptr->path); //} }
internal static void io_puts_ary(Array ary, IO io, Frame caller) { foreach (object element in ary) if (Array.IsInspecting(element)) Ruby.Methods.rb_io_puts.singleton.Calln(null, io, caller, new ArgList(null, new object[] { new String("[...]") })); else Ruby.Methods.rb_io_puts.singleton.Calln(null, io, caller, new ArgList(null, new object[] { element })); }
private static void pipe_add_fptr(IO fptr) { pipe_list list = new pipe_list(fptr, _pipe_list); _pipe_list = list; }
internal static long io_tell(IO fptr) { return flush_before_seek(fptr).f.Position; }
private static void pipe_del_fptr(IO fptr) { pipe_list list = _pipe_list; pipe_list tmp; if (list.fptr == fptr) { _pipe_list = list.next; list = null; return; } while (list.next != null) { if (list.next.fptr == fptr) { tmp = list.next; list.next = list.next.next; tmp = null; return; } list = list.next; } }
internal static IO rb_file_open(Frame caller, string fname, string mode) { IO io = new IO(Ruby.Runtime.Init.rb_cIO); int mode1 = IO.rb_io_mode_flags(caller, mode); int mode2 = rb_io_mode_modenum(caller, mode); FileMode fm = IO.modenumToFileMode(mode2); FileAccess fa = IO.modenumToFileAccess(mode2); io.Init(fname, fm, fa, mode1); return io; }
private static void pipe_finalize(IO fptr, bool noraise) { fptr_finalize(fptr, noraise); pipe_del_fptr(fptr); }
internal static void rb_io_check_initialized(Frame caller, IO fptr) { if (fptr == null) throw new IOError("uninitialized stream").raise(caller); }
internal pipe_list(IO fptr, pipe_list next) { this.fptr = fptr; this.next = next; }
internal static void rb_io_check_writable(Frame caller, IO fptr) { rb_io_check_closed(caller, fptr); if ((fptr.mode & FMODE_WRITABLE) == 0) throw new IOError("not opened for writing").raise(caller); if ((fptr.mode & FMODE_RBUF) > 0 && fptr.f.Position < fptr.f.Length && fptr.f2 != null) { io_seek(fptr, 0, SEEK_CUR); } if (fptr.f2 != null) { fptr.mode &= ~FMODE_RBUF; } }
private static int skip_file_header(Frame caller, IO f, out string line) { int line_start = 1; while ((line = f.ReadLine(caller)) != null) { line_start++; if (line.StartsWith("#!") && line.Contains("ruby")) return line_start; } throw new LoadError("No Ruby script found in input").raise(caller); }