Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
41 changes: 36 additions & 5 deletions src/host_fst.c
Original file line number Diff line number Diff line change
Expand Up @@ -406,6 +406,14 @@ static char *get_path2(void) {
return NULL;
}

#if defined (__linux__)
static void get_resource_pathname(const char *path, char *rpath) {
char *pos=strrchr(path,'/');
strncpy(rpath, path, (pos-path)+1);
strcat(rpath, "._");
strcat(rpath, pos+1);
}
#endif

/*
* shutdown is called when switching to p8.
Expand Down Expand Up @@ -546,6 +554,17 @@ static word32 fst_destroy(int class, const char *path) {
int ok = S_ISDIR(st.st_mode) ? rmdir(path) : unlink(path);


#if defined(__linux__)
if (! S_ISDIR(st.st_mode)) {
// on linux remove the resource fork file as well.
char rpath[1024];
get_resource_pathname(path, rpath);
if (stat(rpath, &st) == 0) {
int ok2 = unlink(rpath);
if (ok2 < 0) return host_map_errno_path(errno, path);
}
}
#endif
if (ok < 0) return host_map_errno_path(errno, path);
return 0;
}
Expand Down Expand Up @@ -768,12 +787,18 @@ static int open_data_fork(const char *path, word16 *access, word16 *error) {

return fd;
}
#if defined(__APPLE__) || defined(__linux__)
static int open_resource_fork(const char *path, word16 *access, word16 *error) {
#if defined(__APPLE__)
static int open_resource_fork(const char *path, word16 *access, word16 *error) {
// os x / hfs/apfs don't need to specifically create a resource fork.
// or do they?

char *rpath = host_gc_append_path(path, _PATH_RSRCFORKSPEC);
#else
char rpath[1024];
get_resource_pathname(path, rpath);
#endif

int fd = -1;
for (;;) {
Expand Down Expand Up @@ -852,11 +877,6 @@ static int open_resource_fork(const char *path, word16 *access, word16 *error) {

return fd;
}
#elif defined __linux__
static int open_resource_fork(const char *path, word16 *access, word16 *error) {
*error = resForkNotFound;
return -1;
}
#else
static int open_resource_fork(const char *path, word16 *access, word16 *error) {
*error = resForkNotFound;
Expand Down Expand Up @@ -1534,9 +1554,20 @@ static word32 fst_change_path(int class, const char *path1, const char *path2) {
return invalidAccess;

// rename will delete any previous file. ChangePath should return an error.
#if ! defined(__linux__)
if (stat(path2, &st) == 0) return dupPathname;

if (rename(path1, path2) < 0) return host_map_errno_path(errno, path2);
#else
//on linux rename both the file and the resource file.
char rpath1[1024], rpath2[1024];
get_resource_pathname(path1, rpath1);
get_resource_pathname(path2, rpath2);
if (stat(path2, &st) == 0 || stat(rpath2, &st) == 0) return dupPathname;
if (rename(path1, path2) < 0) return host_map_errno_path(errno, path2);
if (rename(rpath1, rpath2) < 0) return host_map_errno_path(errno, rpath2);

#endif
return 0;
}

Expand Down
25 changes: 20 additions & 5 deletions src/unix_host_common.c
Original file line number Diff line number Diff line change
Expand Up @@ -256,10 +256,25 @@ void host_get_file_xinfo(const char *path, struct file_info *fi) {
void host_get_file_xinfo(const char *path, struct file_info *fi) {

ssize_t tmp;
tmp = getxattr(path, "user.com.apple.ResourceFork", NULL, 0);
if (tmp < 0) tmp = 0;
fi->resource_eof = tmp;
fi->resource_blocks = (tmp + 511) / 512;
struct stat st;
char rpath[1024] = {0};
char *pos=strrchr(path,'/');
if (pos) {
strncpy(rpath, path, (pos-path)+1);
} else {
pos = (char *)path - 1;
}
strcat(rpath, "._");
strcat(rpath, pos+1);

int ok = stat(rpath, &st);
if (ok < 0) {
fi->resource_eof = 0;
fi->resource_blocks = 0;
} else {
fi->resource_eof = st.st_size;
fi->resource_blocks = st.st_blocks;
}

tmp = getxattr(path, "user.com.apple.FinderInfo", fi->finder_info, 32);
if (tmp == 16 || tmp == 32) {
Expand Down Expand Up @@ -398,7 +413,7 @@ word32 host_set_file_info(const char *path, struct file_info *fi) {
word32 host_set_file_info(const char *path, struct file_info *fi) {

if (fi->has_fi && fi->storage_type != 0x0d) {
int ok = setxattr(path, "user.apple.FinderInfo", fi->finder_info, 32, 0);
int ok = setxattr(path, "user.com.apple.FinderInfo", fi->finder_info, 32, 0);
if (ok < 0) return host_map_errno(errno);
}

Expand Down