implement File.setExecutable(), File.canExecute(), and File.createTempFile()

This commit is contained in:
Joshua Warner 2012-02-09 14:04:42 -07:00
parent 33976d1ba4
commit bbb4529752
4 changed files with 127 additions and 1 deletions

View File

@ -32,10 +32,13 @@
# define STAT _wstat
# define STRUCT_STAT struct _stat
# define MKDIR(path, mode) _wmkdir(path)
# define CHMOD(path, mode) _wchmod(path, mode)
# define UNLINK _wunlink
# define RENAME _wrename
# define OPEN_MASK O_BINARY
# define CHECK_X_OK R_OK
# ifdef _MSC_VER
# define S_ISREG(x) ((x) & _S_IFREG)
# define S_ISDIR(x) ((x) & _S_IFDIR)
@ -67,11 +70,14 @@ typedef wchar_t char_t;
# define STAT stat
# define STRUCT_STAT struct stat
# define MKDIR mkdir
# define CHMOD chmod
# define CREAT creat
# define UNLINK unlink
# define RENAME rename
# define OPEN_MASK 0
# define CHECK_X_OK X_OK
# define GET_CHARS GetStringUTFChars
# define RELEASE_CHARS ReleaseStringUTFChars
@ -442,6 +448,64 @@ Java_java_io_File_canWrite(JNIEnv* e, jclass, jstring path)
return false;
}
extern "C" JNIEXPORT jboolean JNICALL
Java_java_io_File_canExecute(JNIEnv* e, jclass, jstring path)
{
string_t chars = getChars(e, path);
if (chars) {
int r = ACCESS(chars, CHECK_X_OK);
releaseChars(e, path, chars);
return (r == 0);
}
return false;
}
#ifndef PLATFORM_WINDOWS
extern "C" JNIEXPORT jboolean JNICALL
Java_java_io_File_setExecutable(JNIEnv* e, jclass, jstring path, jboolean executable, jboolean ownerOnly)
{
string_t chars = getChars(e, path);
if(chars) {
jboolean v;
int mask;
if(ownerOnly) {
mask = S_IXUSR;
} else {
mask = S_IXUSR | S_IXGRP | S_IXOTH;
}
STRUCT_STAT s;
int r = STAT(chars, &s);
if(r == 0) {
int mode = s.st_mode;
if(executable) {
mode |= mask;
} else {
mode &= ~mask;
}
if(CHMOD(chars, mode) != 0) {
v = false;
} else {
v = true;
}
} else {
v = false;
}
releaseChars(e, path, chars);
return v;
}
return false;
}
#else // ifndef PLATFORM_WINDOWS
extern "C" JNIEXPORT jboolean JNICALL
Java_java_io_File_setExecutable(JNIEnv*, jclass, jstring, jboolean executable, jboolean)
{
return executable;
}
#endif
extern "C" JNIEXPORT jboolean JNICALL
Java_java_io_File_rename(JNIEnv* e, jclass, jstring old, jstring new_)

View File

@ -35,6 +35,38 @@ public class File implements Serializable {
this(parent.getPath() + FileSeparator + child);
}
public static File createTempFile(String prefix, String suffix) {
return createTempFile(prefix, suffix, null);
}
public static File createTempFile(String prefix, String suffix, File directory) {
if(directory == null) {
directory = new File(System.getProperty("java.io.tmpdir"));
}
if(suffix == null) {
suffix = ".tmp";
}
File ret;
long state = System.currentTimeMillis();
do {
ret = generateFile(directory, prefix, state, suffix);
state *= 7;
state += 3;
} while(ret == null);
ret.createNewFile();
return ret;
}
private static File generateFile(File directory, String prefix, long state, String suffix) {
File ret = new File(directory, prefix + state + suffix);
if(ret.exists()) {
return null;
} else {
return ret;
}
}
private static String normalize(String path) {
if ("\\".equals(FileSeparator)) {
return path.replace('/', '\\');
@ -76,6 +108,22 @@ public class File implements Serializable {
public boolean canWrite() {
return canWrite(path);
}
private static native boolean canExecute(String path);
public boolean canExecute() {
return canExecute(path);
}
private static native boolean setExecutable(String path, boolean executable, boolean ownerOnly);
public boolean setExecutable(boolean executable) {
return setExecutable(executable, true);
}
public boolean setExecutable(boolean executable, boolean ownerOnly) {
return setExecutable(path, executable, ownerOnly);
}
public String getName() {
int index = path.lastIndexOf(FileSeparator);

View File

@ -1,4 +1,4 @@
MAKEFLAGS = -s
#MAKEFLAGS = -s
name = avian
version = 0.5

View File

@ -20,10 +20,24 @@ public class Files {
}
}
private static void setExecutableTestWithPermissions(boolean executable) {
File file = File.createTempFile("avian.", null);
file.setExecutable(executable);
if (executable) {
expect(file.canExecute());
} else {
// Commented out because this will fail on Windows - both on Avian and on OpenJDK
// The implementation for Windows considers canExecute() to be the same as canRead()
// expect(!file.canExecute());
}
}
public static void main(String[] args) {
isAbsoluteTest(true);
isAbsoluteTest(false);
setExecutableTestWithPermissions(true);
setExecutableTestWithPermissions(false);
}
}