Start line:  
End line:  

Snippet Preview

Snippet HTML Code

Stack Overflow Questions
BEGIN LICENSE BLOCK ***** Version: CPL 1.0/GPL 2.0/LGPL 2.1 The contents of this file are subject to the Common Public License Version 1.0 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.eclipse.org/legal/cpl-v10.html Software distributed under the License is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License for the specific language governing rights and limitations under the License. Copyright (C) 2002-2004 Anders Bengtsson <ndrsbngtssn@yahoo.se> Copyright (C) 2002-2004 Jan Arne Petersen <jpetersen@uni-bonn.de> Copyright (C) 2004 Thomas E Enebo <enebo@acm.org> Copyright (C) 2004-2005 Charles O Nutter <headius@headius.com> Copyright (C) 2004 Stefan Matthias Aust <sma@3plus4.de> Alternatively, the contents of this file may be used under the terms of either of the GNU General Public License Version 2 or later (the "GPL"), or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"), in which case the provisions of the GPL or the LGPL are applicable instead of those above. If you wish to allow use of your version of this file only under the terms of either the GPL or the LGPL, and not to allow others to use your version of this file under the terms of the CPL, indicate your decision by deleting the provisions above and replace them with the notice and other provisions required by the GPL or the LGPL. If you do not delete the provisions above, a recipient may use your version of this file under the terms of any one of the CPL, the GPL or the LGPL. END LICENSE BLOCK ***
 
 package org.jruby;
 
 import static org.jruby.RubyEnumerator.enumeratorize;
 
 import java.io.File;
 import java.util.List;
 
 
 import static org.jruby.CompatVersion.*;

.The Ruby built-in class Dir.

Author(s):
jvoegele
 
 @JRubyClass(name = "Dir", include = "Enumerable")
 public class RubyDir extends RubyObject {
     private RubyString path;       // What we passed to the constructor for method 'path'
     protected JRubyFile dir;
     private long lastModified = .;
     private String[] snapshot;     // snapshot of contents of directory
     private int pos;               // current position in directory
     private boolean isOpen = true;
 
     private final static Encoding UTF8 = .;
 
     public RubyDir(Ruby runtimeRubyClass type) {
         super(runtimetype);
     }
 
     private static final ObjectAllocator DIR_ALLOCATOR = new ObjectAllocator() {
         public IRubyObject allocate(Ruby runtimeRubyClass klass) {
             return new RubyDir(runtimeklass);
         }
     };
 
     public static RubyClass createDirClass(Ruby runtime) {
         RubyClass dirClass = runtime.defineClass("Dir"runtime.getObject(), );
         runtime.setDir(dirClass);
 
         dirClass.index = .;
         dirClass.setReifiedClass(RubyDir.class);
 
        dirClass.includeModule(runtime.getEnumerable());
        dirClass.defineAnnotatedMethods(RubyDir.class);
        return dirClass;
    }
    private final void checkDir() {
        testFrozen("Dir");
        update();
        if (!throw getRuntime().newIOError("closed directory");
    }
    private void update() {
        if ( == null || .exists() && .lastModified() > ) {
             = .lastModified();
            List<StringsnapshotList = new ArrayList<String>();
            snapshotList.add(".");
            snapshotList.add("..");
            snapshotList.addAll(getContents());
             = (String[]) snapshotList.toArray(new String[snapshotList.size()]);
        }
    }

    
Creates a new Dir. This method takes a snapshot of the contents of the directory at creation time, so changes to the contents of the directory will not be reflected during the lifetime of the Dir object returned, so a new Dir instance must be created to reflect changes to the underlying file system.
    @JRubyMethod(compat = )
    public IRubyObject initialize(IRubyObject arg) {
        RubyString newPath = arg.convertToString();
         = newPath;
         = 0;
        String adjustedPath = RubyFile.adjustRootPathOnWindows(getRuntime(), newPath.toString(), null);
        checkDirIsTwoSlashesOnWindows(getRuntime(), adjustedPath);
         = JRubyFile.create(getRuntime().getCurrentDirectory(), adjustedPath);
        List<StringsnapshotList = RubyDir.getEntries(getRuntime(), adjustedPath);
         = (String[]) snapshotList.toArray(new String[snapshotList.size()]);
        return this;
    }
    @JRubyMethod(name = "initialize", compat = )
    public IRubyObject initialize19(IRubyObject arg) {
        return initialize(RubyFile.get_path(getRuntime().getCurrentContext(), arg));
    }
// ----- Ruby Class Methods ----------------------------------------------------
    private static List<ByteListdirGlobs(ThreadContext contextString cwdIRubyObject[] argsint flags) {
        List<ByteListdirs = new ArrayList<ByteList>();
        for (int i = 0; i < args.lengthi++) {
            dirs.addAll(Dir.push_glob(cwdglobArgumentAsByteList(contextargs[i]), flags));
        }
        return dirs;
    }
    private static IRubyObject asRubyStringList(Ruby runtimeList<ByteListdirs) {
        List<RubyStringallFiles = new ArrayList<RubyString>();
        Encoding enc = runtime.getDefaultExternalEncoding();
        if (enc == null) {
            enc = ;
        }
        for (ByteList dir : dirs) {
            allFiles.add(RubyString.newString(runtimedirenc));
        }
        IRubyObject[] tempFileList = new IRubyObject[allFiles.size()];
        allFiles.toArray(tempFileList);
        return runtime.newArrayNoCopy(tempFileList);
    }
    private static String getCWD(Ruby runtime) {
        try {
            return new org.jruby.util.NormalizedFile(runtime.getCurrentDirectory()).getCanonicalPath();
        } catch (Exception e) {
            return runtime.getCurrentDirectory();
        }
    }
    @JRubyMethod(name = "[]", required = 1, rest = true, meta = true)
    public static IRubyObject aref(ThreadContext contextIRubyObject recvIRubyObject[] args) {
        Ruby runtime = context.runtime;
        List<ByteListdirs;
        if (args.length == 1) {
            Pattern pattern = Pattern.compile("file:(.*)!/(.*)");
            String glob = args[0].toString();
            Matcher matcher = pattern.matcher(glob);
            if (matcher.find()) {
                String jarFileName = matcher.group(1);
                String jarUri = "file:" + jarFileName + "!/";
                String fileGlobString = matcher.group(2);
                String filePatternString = convertGlobToRegEx(fileGlobString);
                Pattern filePattern = Pattern.compile(filePatternString);
                try {
                    JarFile jarFile = new JarFile(jarFileName);
                    List<RubyStringallFiles = new ArrayList<RubyString>();
                    Enumeration<JarEntryentries = jarFile.entries();
                    while (entries.hasMoreElements()) {
                        String entry = entries.nextElement().getName();
                        String chomped_entry = entry.endsWith("/") ? entry.substring(0, entry.length() - 1) : entry;
                        if (filePattern.matcher(chomped_entry).find()) {
                            allFiles.add(RubyString.newString(runtimejarUri + chomped_entry.toString()));
                        }
                    }
                    IRubyObject[] tempFileList = new IRubyObject[allFiles.size()];
                    allFiles.toArray(tempFileList);
                    return runtime.newArrayNoCopy(tempFileList);
                } catch (IOException e) {
                    return runtime.newArrayNoCopy(new IRubyObject[0]);
                }
            }
            dirs = Dir.push_glob(getCWD(runtime), globArgumentAsByteList(contextargs[0]), 0);
        } else {
            dirs = dirGlobs(contextgetCWD(runtime), args, 0);
        }
        return asRubyStringList(runtimedirs);
    }
    private static ByteList globArgumentAsByteList(ThreadContext contextIRubyObject arg) {
        if (context.runtime.is1_9()) return RubyFile.get_path(contextarg).getByteList();
        return arg.convertToString().getByteList();
    }
    private static String convertGlobToRegEx(String line) {
        line = line.trim();
        StringBuilder sb = new StringBuilder(line.length());
        sb.append("^");
        boolean escaping = false;
        int inCurlies = 0;
        for (char currentChar : line.toCharArray()) {
            switch (currentChar) {
            case '*':
                if (escaping)
                    sb.append("\\*");
                else
                    sb.append("[^/]*");
                escaping = false;
                break;
            case '?':
                if (escaping)
                    sb.append("\\?");
                else
                    sb.append('.');
                escaping = false;
                break;
            case '.':
            case '(':
            case ')':
            case '+':
            case '|':
            case '^':
            case '$':
            case '@':
            case '%':
                sb.append('\\');
                sb.append(currentChar);
                escaping = false;
                break;
            case '\\':
                if (escaping) {
                    sb.append("\\\\");
                    escaping = false;
                } else
                    escaping = true;
                break;
            case '{':
                if (escaping) {
                    sb.append("\\{");
                } else {
                    sb.append('(');
                    inCurlies++;
                }
                escaping = false;
                break;
            case '}':
                if (inCurlies > 0 && !escaping) {
                    sb.append(')');
                    inCurlies--;
                } else if (escaping)
                    sb.append("\\}");
                else
                    sb.append("}");
                escaping = false;
                break;
            case ',':
                if (inCurlies > 0 && !escaping) {
                    sb.append('|');
                } else if (escaping)
                    sb.append("\\,");
                else
                    sb.append(",");
                break;
            default:
                escaping = false;
                sb.append(currentChar);
            }
        }
        sb.append("$");
        return sb.toString().replace("[^/]*[^/]*/"".*").replace("[^/]*[^/]*"".*");
    }

    
Returns an array of filenames matching the specified wildcard pattern pat. If a block is given, the array is iterated internally with each filename is passed to the block in turn. In this case, Nil is returned.
    @JRubyMethod(required = 1, optional = 1, meta = true)
    public static IRubyObject glob(ThreadContext contextIRubyObject recvIRubyObject[] argsBlock block) {
        Ruby runtime = context.runtime;
        int flags = args.length == 2 ? RubyNumeric.num2int(args[1]) : 0;
        List<ByteListdirs;
        IRubyObject tmp = args[0].checkArrayType();
        if (tmp.isNil()) {
            dirs = Dir.push_glob(runtime.getCurrentDirectory(), globArgumentAsByteList(contextargs[0]), flags);
        } else {
            dirs = dirGlobs(contextgetCWD(runtime), ((RubyArraytmp).toJavaArray(), flags);
        }
        if (block.isGiven()) {
            for (int i = 0; i < dirs.size(); i++) {
                Encoding enc = runtime.getDefaultExternalEncoding();
                if (enc == null) {
                    enc = ;
                }
                block.yield(context, RubyString.newString(runtimedirs.get(i), enc));
            }
            return runtime.getNil();
        }
        return asRubyStringList(runtimedirs);
    }

    

Returns:
all entries for this Dir
    @JRubyMethod(name = "entries")
    public RubyArray entries() {
        return getRuntime().newArrayNoCopy(JavaUtil.convertJavaArrayToRuby(getRuntime(), ));
    }

    
Returns an array containing all of the filenames in the given directory.
    @JRubyMethod(name = "entries", meta = true, compat = )
    public static RubyArray entries(IRubyObject recvIRubyObject path) {
        return entriesCommon(recv.getRuntime(), path.convertToString().getUnicodeValue());
    }
    @JRubyMethod(name = "entries", meta = true, compat = )
    public static RubyArray entries19(ThreadContext contextIRubyObject recvIRubyObject arg) {
        return entriesCommon(context.runtime, RubyFile.get_path(contextarg).asJavaString());
    }
    @JRubyMethod(name = "entries", meta = true, compat = )
    public static RubyArray entries19(ThreadContext contextIRubyObject recvIRubyObject argIRubyObject opts) {
        // FIXME: do something with opts
        return entriesCommon(context.runtime, RubyFile.get_path(contextarg).asJavaString());
    }
    private static RubyArray entriesCommon(Ruby runtimeString path) {
        String adjustedPath = RubyFile.adjustRootPathOnWindows(runtimepathnull);
        checkDirIsTwoSlashesOnWindows(runtimeadjustedPath);
        Object[] files = getEntries(runtimeadjustedPath).toArray();
        return runtime.newArrayNoCopy(JavaUtil.convertJavaArrayToRuby(runtimefiles));
    }
    private static List<StringgetEntries(Ruby runtimeString path) {
        if (!RubyFileTest.directory_p(runtime, RubyString.newString(runtimepath)).isTrue()) {
            throw runtime.newErrnoENOENTError("No such directory: " + path);
        }
        if (path.startsWith("file:")) return entriesIntoAJarFile(runtimepath);
        return entriesIntoADirectory(runtimepath);
    }
    private static List<StringentriesIntoADirectory(Ruby runtimeString path) {
        final JRubyFile directory = JRubyFile.create(runtime.getCurrentDirectory(), path);
        List<StringfileList = getContents(directory);
        fileList.add(0, ".");
        fileList.add(1, "..");
        return fileList;
    }
    private static List<StringentriesIntoAJarFile(Ruby runtimeString path) {
        String file = path.substring(5);
        int bang = file.indexOf('!');
        if (bang == -1) {
          return entriesIntoADirectory(runtimepath.substring(5));
        }
        if (bang == file.length() - 1) {
            return new ArrayList<String>();
        }
        String jar = file.substring(0, bang);
        String after = file.substring(bang + 2);
        JarFile jf;
        try {
            jf = new JarFile(jar);
        } catch (IOException e) {
            throw new RuntimeException("Valid JAR file expected"e);
        }
        List<StringfileList = new ArrayList<String>();
        Enumeration<? extends ZipEntryentries = jf.entries();
        while (entries.hasMoreElements()) {
            String zipEntry = entries.nextElement().getName();
            if (zipEntry.matches(after + "/" + "[^/]+")) {
                fileList.add(zipEntry.substring(after.length() + 1));
            }
        }
        return fileList;
    }
    // MRI behavior: just plain '//' or '\\\\' are considered illegal on Windows.
    private static void checkDirIsTwoSlashesOnWindows(Ruby runtimeString path) {
        if (. && ("//".equals(path) || "\\\\".equals(path))) {
            throw runtime.newErrnoEINVALError("Invalid argument - " + path);
        }
    }

    
Changes the current directory to path
    @JRubyMethod(optional = 1, meta = true)
    public static IRubyObject chdir(ThreadContext contextIRubyObject recvIRubyObject[] argsBlock block) {
        Ruby runtime = context.runtime;
        RubyString path = args.length == 1 ?
            RubyFile.get_path(contextargs[0]) : getHomeDirectoryPath(context);
        String adjustedPath = RubyFile.adjustRootPathOnWindows(runtimepath.asJavaString(), null);
        checkDirIsTwoSlashesOnWindows(runtimeadjustedPath);
        JRubyFile dir = getDir(runtimeadjustedPathtrue);
        String realPath = null;
        String oldCwd = runtime.getCurrentDirectory();
        // We get canonical path to try and flatten the path out.
        // a dir '/subdir/..' should return as '/'
        // cnutter: Do we want to flatten path out?
        try {
            realPath = dir.getCanonicalPath();
        } catch (IOException e) {
            realPath = dir.getAbsolutePath();
        }
        IRubyObject result = null;
        if (block.isGiven()) {
            // FIXME: Don't allow multiple threads to do this at once
            runtime.setCurrentDirectory(realPath);
            try {
                result = block.yield(contextpath);
            } finally {
                dir = getDir(runtimeoldCwdtrue);
                runtime.setCurrentDirectory(oldCwd);
            }
        } else {
            runtime.setCurrentDirectory(realPath);
            result = runtime.newFixnum(0);
        }
        return result;
    }

    
Changes the root directory (only allowed by super user). Not available on all platforms.
    @JRubyMethod(name = "chroot", required = 1, meta = true)
    public static IRubyObject chroot(IRubyObject recvIRubyObject path) {
        throw recv.getRuntime().newNotImplementedError("chroot not implemented: chroot is non-portable and is not supported.");
    }

    
Deletes the directory specified by path. The directory must be empty.
    @JRubyMethod(name = {"rmdir""unlink""delete"}, required = 1, meta = true, compat = )
    public static IRubyObject rmdir(IRubyObject recvIRubyObject path) {
        return rmdirCommon(recv.getRuntime(), path.convertToString().getUnicodeValue());
    }
    @JRubyMethod(name = {"rmdir""unlink""delete"}, required = 1, meta = true, compat = )
    public static IRubyObject rmdir19(ThreadContext contextIRubyObject recvIRubyObject path) {
        return rmdirCommon(context.runtime, RubyFile.get_path(contextpath).asJavaString());
    }
    private static IRubyObject rmdirCommon(Ruby runtimeString path) {
        JRubyFile directory = getDirForRmdir(runtimepath);
        // at this point, only thing preventing delete should be non-emptiness
        if (runtime.getPosix().rmdir(directory.toString()) < 0) {
            throw runtime.newErrnoENOTEMPTYError(path);
        }
        return runtime.newFixnum(0);
    }

    
Executes the block once for each file in the directory specified by path.
    @JRubyMethod(meta = true, compat = )
    public static IRubyObject foreach(ThreadContext contextIRubyObject recvIRubyObject _pathBlock block) {
        RubyString pathString = _path.convertToString();
        return foreachCommon(contextrecvcontext.runtimepathStringblock);
    }
    @JRubyMethod(name = "foreach", meta = true, compat = )
    public static IRubyObject foreach19(ThreadContext contextIRubyObject recvIRubyObject argBlock block) {
        RubyString pathString = RubyFile.get_path(contextarg);
        return foreachCommon(contextrecvcontext.runtimepathStringblock);
    }
    private static IRubyObject foreachCommon(ThreadContext contextIRubyObject recvRuby runtimeRubyString _pathBlock block) {
        if (block.isGiven()) {
            RubyClass dirClass = runtime.getDir();
            RubyDir dir = (RubyDirdirClass.newInstance(contextnew IRubyObject[]{_path}, block);
            dir.each(contextblock);
            return runtime.getNil();
        }
        return enumeratorize(runtimerecv"foreach"_path);
    }

    
Returns the current directory.
    @JRubyMethod(name = {"getwd""pwd"}, meta = true)
    public static RubyString getwd(IRubyObject recv) {
        Ruby ruby = recv.getRuntime();
        RubyString pwd = RubyString.newUnicodeString(rubygetCWD(ruby));
        pwd.setTaint(true);
        return pwd;
    }

    
Returns the home directory of the current user or the named user if given.
    @JRubyMethod(name = "home", optional = 1, meta = true, compat = )
    public static IRubyObject home(ThreadContext contextIRubyObject recvIRubyObject[] args) {
        if (args.length > 0) return getHomeDirectoryPath(contextargs[0].toString());
        return getHomeDirectoryPath(context);
    }

    
Creates the directory specified by path. Note that the mode parameter is provided only to support existing Ruby code, and is ignored.
    @JRubyMethod(name = "mkdir", required = 1, optional = 1, meta = true, compat = )
    public static IRubyObject mkdir(IRubyObject recvIRubyObject[] args) {
        Ruby runtime = recv.getRuntime();
        RubyString stringArg = args[0].convertToString();
        return mkdirCommon(runtimestringArg.getUnicodeValue(), args);
    }
    @JRubyMethod(name = "mkdir", required = 1, optional = 1, meta = true, compat = )
    public static IRubyObject mkdir19(ThreadContext contextIRubyObject recvIRubyObject[] args) {
        return mkdirCommon(context.runtime, RubyFile.get_path(contextargs[0]).asJavaString(), args);
    }
    private static IRubyObject mkdirCommon(Ruby runtimeString pathIRubyObject[] args) {
        File newDir = getDir(runtimepathfalse);
        if (. == '\\'newDir = new File(newDir.getPath());
        int mode = args.length == 2 ? ((intargs[1].convertToInteger().getLongValue()) : 0777;
        if (runtime.getPosix().mkdir(newDir.getAbsolutePath(), mode) < 0) {
            // FIXME: This is a system error based on errno
            throw runtime.newSystemCallError("mkdir failed");
        }
        return RubyFixnum.zero(runtime);
    }

    
Returns a new directory object for path. If a block is provided, a new directory object is passed to the block, which closes the directory object before terminating.
    @JRubyMethod(meta = true, compat = )
    public static IRubyObject open(ThreadContext contextIRubyObject recvIRubyObject pathBlock block) {
        RubyDir directory = (RubyDircontext.runtime.getDir().newInstance(context,
                new IRubyObject[]{path}, .);
        if (!block.isGiven()) return directory;
        try {
            return block.yield(contextdirectory);
        } finally {
            directory.close();
        }
    }
    @JRubyMethod(name = "open", meta = true, compat = )
    public static IRubyObject open19(ThreadContext contextIRubyObject recvIRubyObject pathBlock block) {
        return open(contextrecv, RubyFile.get_path(contextpath), block);
    }
// ----- Ruby Instance Methods -------------------------------------------------
    
Closes the directory stream.
    @JRubyMethod(name = "close")
    public IRubyObject close() {
        // Make sure any read()s after close fail.
        checkDir();
         = false;
        return getRuntime().getNil();
    }

    
Executes the block once for each entry in the directory.
    public IRubyObject each(ThreadContext contextBlock block) {
        checkDir();
        String[] contents = ;
        for ( = 0;  < contents.length++) {
            block.yield(contextgetRuntime().newString(contents[]));
        }
        return this;
    }
    @JRubyMethod(name = "each")
    public IRubyObject each19(ThreadContext contextBlock block) {
        return block.isGiven() ? each(contextblock) : enumeratorize(context.runtimethis"each");
    }
    @Override
    public IRubyObject inspect() {
        Ruby runtime = getRuntime();
        StringBuilder part = new StringBuilder();
        String cname = getMetaClass().getRealClass().getName();
        part.append("#<").append(cname).append(":").append(.asJavaString()).append(">");
        return runtime.newString(part.toString());
    }

    
Returns the current position in the directory.
    @JRubyMethod(name = {"tell""pos"})
    public RubyInteger tell() {
        checkDir();
        return getRuntime().newFixnum();
    }

    
Moves to a position d. pos must be a value returned by tell or 0.
    @JRubyMethod(name = "seek", required = 1)
    public IRubyObject seek(IRubyObject newPos) {
        checkDir();
        set_pos(newPos);
        return this;
    }
    @JRubyMethod(name = "pos=", required = 1)
    public IRubyObject set_pos(IRubyObject newPos) {
        int pos2 = RubyNumeric.fix2int(newPos);
        if (pos2 >= 0) this. = pos2;
        return newPos;
    }
    @JRubyMethod(name = "path")
    public IRubyObject path(ThreadContext context) {
        return .strDup(context.runtime);
    }

    
Returns the next entry from this directory.
    @JRubyMethod(name = "read")
    public IRubyObject read() {
        checkDir();
        if ( >= .return getRuntime().getNil();
        RubyString result = getRuntime().newString([]);
        ++;
        return result;
    }

    
Moves position in this directory to the first entry.
    @JRubyMethod(name = "rewind")
    public IRubyObject rewind() {
        checkDir();
         = 0;
        return this;
    }
    @JRubyMethod(name = {"exists?""exist?"}, meta = true, compat = )
    public static IRubyObject exist(ThreadContext contextIRubyObject recvIRubyObject arg) {
        try {
            return context.runtime.newFileStat(RubyFile.get_path(contextarg).asJavaString(), false).directory_p();
        } catch (Exception e) {
            return context.runtime.newBoolean(false);
        }
    }
// ----- Helper Methods --------------------------------------------------------
    
Returns a Java File object for the specified path. If path is not a directory, throws IOError.

Parameters:
path path for which to return the File object.
mustExist is true the directory must exist. If false it must not.
Throws:
IOError if path is not a directory.
    protected static JRubyFile getDir(final Ruby runtimefinal String pathfinal boolean mustExist) {
        String dir = dirFromPath(pathruntime);
        JRubyFile result = JRubyFile.create(runtime.getCurrentDirectory(), dir);
        if (mustExist && !result.exists()) {
            throw runtime.newErrnoENOENTError(dir);
        }
        boolean isDirectory = result.isDirectory();
        if (mustExist && !isDirectory) {
            throw runtime.newErrnoENOTDIRError(path);
        }
        if (!mustExist && isDirectory) {
            throw runtime.newErrnoEEXISTError(dir);
        }
        return result;
    }

    
Similar to getDir, but performs different checks to match rmdir behavior.

Parameters:
runtime
path
mustExist
Returns:
    protected static JRubyFile getDirForRmdir(final Ruby runtimefinal String path) {
        String dir = dirFromPath(pathruntime);
        JRubyFile directory = JRubyFile.create(runtime.getCurrentDirectory(), dir);
        // Order is important here...File.exists() will return false if the parent
        // dir can't be read, so we check permissions first
        // no permission
        if (directory.getParentFile().exists() &&
                !directory.getParentFile().canWrite()) {
            throw runtime.newErrnoEACCESError(path);
        }
        // Since we transcode we depend on posix to lookup stat stuff since
        // java.io.File does not seem to cut it.  A failed stat will throw ENOENT.
        FileStat stat = runtime.getPosix().stat(directory.toString());
        // is not directory
        if (!stat.isDirectory()) throw runtime.newErrnoENOTDIRError(path);
        return directory;
    }
    private static String dirFromPath(final String pathfinal Ruby runtimethrows RaiseException {
        String dir = path;
        String[] pathParts = RubyFile.splitURI(path);
        if (pathParts != null) {
            if (pathParts[0].equals("file:") && pathParts[1].length() > 0 && pathParts[1].indexOf("!/") == -1) {
                dir = pathParts[1];
            } else {
                throw runtime.newErrnoENOTDIRError(dir);
            }
        }
        return dir;
    }

    
Returns the contents of the specified directory as an ArrayList containing the names of the files as Java Strings.
    protected static List<StringgetContents(File directory) {
        String[] contents = directory.list();
        List<Stringresult = new ArrayList<String>();
        // If an IO exception occurs (something odd, but possible)
        // A directory may return null.
        if (contents != null) {
            for (int i = 0; i < contents.lengthi++) {
                result.add(contents[i]);
            }
        }
        return result;
    }

    
Returns the contents of the specified directory as an ArrayList containing the names of the files as Ruby Strings.
    protected static List<RubyStringgetContents(File directoryRuby runtime) {
        List<RubyStringresult = new ArrayList<RubyString>();
        String[] contents = directory.list();
        for (int i = 0; i < contents.lengthi++) {
            result.add(runtime.newString(contents[i]));
        }
        return result;
    }

    
Returns the home directory of the specified user on the system. If the home directory of the specified user cannot be found, an ArgumentError it thrown.
    public static IRubyObject getHomeDirectoryPath(ThreadContext contextString user) {
        /*
         * TODO: This version is better than the hackish previous one. Windows
         *       behavior needs to be defined though. I suppose this version
         *       could be improved more too.
         * TODO: /etc/passwd is also inadequate for MacOSX since it does not
         *       use /etc/passwd for regular user accounts
         */
        Ruby runtime = context.runtime;
        try {
            // try to use POSIX for this first
            return runtime.newString(runtime.getPosix().getpwnam(user).getHome());
        } catch (Exception e) {
            // otherwise fall back on the old way
            String passwd = null;
            try {
                FileInputStream stream = new FileInputStream("/etc/passwd");
                int totalBytes = stream.available();
                byte[] bytes = new byte[totalBytes];
                stream.read(bytes);
                stream.close();
                passwd = new String(bytes);
            } catch (IOException ioe) {
                return runtime.getNil();
            }
            String[] rows = passwd.split("\n");
            int rowCount = rows.length;
            for (int i = 0; i < rowCounti++) {
                String[] fields = rows[i].split(":");
                if (fields[0].equals(user)) {
                    return runtime.newString(fields[5]);
                }
            }
        }
        throw runtime.newArgumentError("user " + user + " doesn't exist");
    }
    public static RubyString getHomeDirectoryPath(ThreadContext context) {
        Ruby runtime = context.runtime;
        IRubyObject systemHash = runtime.getObject().getConstant("ENV_JAVA");
        RubyHash envHash = (RubyHashruntime.getObject().getConstant("ENV");
        IRubyObject home = null;
        if (home == null || home.isNil()) {
            home = envHash.op_aref(contextruntime.newString("LOGDIR"));
        }
        if (home == null || home.isNil()) {
            home = envHash.op_aref(contextruntime.newString("HOME"));
        }
        if (home == null || home.isNil()) {
            home = systemHash.callMethod(context"[]"runtime.newString("user.home"));
        }
        if (home == null || home.isNil()) {
            throw runtime.newArgumentError("user.home/LOGDIR not set");
        }
        return (RubyStringhome;
    }