if (this == original) return this;
RubyIO originalIO = (RubyIO) TypeConverter.convertToTypeWithCheck(original, runtime.getIO(), "to_io");
OpenFile originalFile = originalIO.getOpenFileChecked();
OpenFile newFile = openFile;
try {
if (originalFile.getPipeStream() != null) {
originalFile.getPipeStream().fflush();
originalFile.getMainStreamSafe().lseek(0, Stream.SEEK_CUR);
} else if (originalFile.isWritable()) {
originalFile.getMainStreamSafe().fflush();
} else {
originalFile.getMainStreamSafe().lseek(0, Stream.SEEK_CUR);
}
newFile.setMode(originalFile.getMode());
newFile.setProcess(originalFile.getProcess());
newFile.setLineNumber(originalFile.getLineNumber());
newFile.setPath(originalFile.getPath());
newFile.setFinalizer(originalFile.getFinalizer());
ModeFlags modes;
if (newFile.isReadable()) {
if (newFile.isWritable()) {
if (newFile.getPipeStream() != null) {
modes = new ModeFlags(ModeFlags.RDONLY);
} else {
modes = new ModeFlags(ModeFlags.RDWR);
}
} else {
modes = new ModeFlags(ModeFlags.RDONLY);
}
} else {
if (newFile.isWritable()) {
modes = new ModeFlags(ModeFlags.WRONLY);
} else {
modes = originalFile.getMainStreamSafe().getModes();
}
}
ChannelDescriptor descriptor = originalFile.getMainStreamSafe().getDescriptor().dup();
newFile.setMainStream(ChannelStream.fdopen(runtime, descriptor, modes));
newFile.getMainStream().setSync(originalFile.getMainStreamSafe().isSync());
// TODO: the rest of this...seeking to same position is unnecessary since we share a channel
// but some of this may be needed?
// fseeko(fptr->f, ftello(orig->f), SEEK_SET);