mirror of
https://github.com/schoebel/mars
synced 2024-12-13 18:25:46 +00:00
main: obey DELETED_STR for non-existing targets
This commit is contained in:
parent
e4a83b9461
commit
570a429c73
@ -2098,6 +2098,7 @@ int run_bone(struct mars_peerinfo *peer, struct mars_dent *remote_dent)
|
|||||||
int status = 0;
|
int status = 0;
|
||||||
struct kstat local_stat = {};
|
struct kstat local_stat = {};
|
||||||
bool stat_ok;
|
bool stat_ok;
|
||||||
|
bool is_deleted;
|
||||||
bool update_mtime = true;
|
bool update_mtime = true;
|
||||||
bool update_ctime = true;
|
bool update_ctime = true;
|
||||||
bool run_trigger = false;
|
bool run_trigger = false;
|
||||||
@ -2123,6 +2124,9 @@ int run_bone(struct mars_peerinfo *peer, struct mars_dent *remote_dent)
|
|||||||
status = mars_stat(remote_dent->d_path, &local_stat, true);
|
status = mars_stat(remote_dent->d_path, &local_stat, true);
|
||||||
stat_ok = (status >= 0);
|
stat_ok = (status >= 0);
|
||||||
|
|
||||||
|
is_deleted = remote_dent->new_link &&
|
||||||
|
!strcmp(remote_dent->new_link, MARS_DELETED_STR);
|
||||||
|
|
||||||
if (stat_ok) {
|
if (stat_ok) {
|
||||||
update_mtime = lamport_time_compare(&remote_dent->new_stat.mtime, &local_stat.mtime) > 0;
|
update_mtime = lamport_time_compare(&remote_dent->new_stat.mtime, &local_stat.mtime) > 0;
|
||||||
update_ctime = lamport_time_compare(&remote_dent->new_stat.ctime, &local_stat.ctime) > 0;
|
update_ctime = lamport_time_compare(&remote_dent->new_stat.ctime, &local_stat.ctime) > 0;
|
||||||
@ -2165,7 +2169,12 @@ int run_bone(struct mars_peerinfo *peer, struct mars_dent *remote_dent)
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
} else if (S_ISLNK(remote_dent->new_stat.mode) && remote_dent->new_link) {
|
} else if (S_ISLNK(remote_dent->new_stat.mode) && remote_dent->new_link) {
|
||||||
if (!stat_ok || update_mtime) {
|
/* Important: not not create .deleted values
|
||||||
|
* unless the object already exists.
|
||||||
|
*/
|
||||||
|
if (is_deleted ?
|
||||||
|
(stat_ok && update_mtime) :
|
||||||
|
(!stat_ok || update_mtime)) {
|
||||||
status = ordered_symlink(remote_dent->new_link,
|
status = ordered_symlink(remote_dent->new_link,
|
||||||
remote_dent->d_path,
|
remote_dent->d_path,
|
||||||
&remote_dent->new_stat.mtime,
|
&remote_dent->new_stat.mtime,
|
||||||
@ -6092,20 +6101,25 @@ static int main_worker(struct mars_global *global, struct mars_dent *dent, bool
|
|||||||
{
|
{
|
||||||
main_worker_fn worker;
|
main_worker_fn worker;
|
||||||
int class = dent->d_class;
|
int class = dent->d_class;
|
||||||
|
bool is_deleted;
|
||||||
|
|
||||||
if (class < 0 || class >= sizeof(main_classes)/sizeof(struct main_class)) {
|
if (class < 0 || class >= sizeof(main_classes)/sizeof(struct main_class)) {
|
||||||
MARS_ERR_ONCE(dent, "bad internal class %d of '%s'\n", class, dent->d_path);
|
MARS_ERR_ONCE(dent, "bad internal class %d of '%s'\n", class, dent->d_path);
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
is_deleted = dent->new_link &&
|
||||||
|
!strcmp(dent->new_link, MARS_DELETED_STR);
|
||||||
|
|
||||||
switch (main_classes[class].cl_type) {
|
switch (main_classes[class].cl_type) {
|
||||||
case 'd':
|
case 'd':
|
||||||
if (!S_ISDIR(dent->new_stat.mode)) {
|
if (!S_ISDIR(dent->new_stat.mode) && !is_deleted) {
|
||||||
MARS_ERR_ONCE(dent, "'%s' should be a directory, but is something else\n", dent->d_path);
|
MARS_ERR_ONCE(dent, "'%s' should be a directory, but is something else\n", dent->d_path);
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 'f':
|
case 'f':
|
||||||
if (!S_ISREG(dent->new_stat.mode)) {
|
if (!S_ISREG(dent->new_stat.mode) && !is_deleted) {
|
||||||
MARS_ERR_ONCE(dent, "'%s' should be a regular file, but is something else\n", dent->d_path);
|
MARS_ERR_ONCE(dent, "'%s' should be a regular file, but is something else\n", dent->d_path);
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
}
|
}
|
||||||
@ -6128,6 +6142,10 @@ static int main_worker(struct mars_global *global, struct mars_dent *dent, bool
|
|||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
default:
|
||||||
|
MARS_ERR_ONCE(dent, "'%s' class %d has unimplemented type %d\n",
|
||||||
|
dent->d_path, class, main_classes[class].cl_type);
|
||||||
|
return -EINVAL;
|
||||||
}
|
}
|
||||||
if (likely(class > CL_ROOT)) {
|
if (likely(class > CL_ROOT)) {
|
||||||
int father = main_classes[class].cl_father;
|
int father = main_classes[class].cl_father;
|
||||||
|
Loading…
Reference in New Issue
Block a user