projects
/
firefly-linux-kernel-4.4.55.git
/ blobdiff
commit
grep
author
committer
pickaxe
?
search:
re
summary
|
shortlog
|
log
|
commit
|
commitdiff
|
tree
raw
|
inline
| side by side
UPSTREAM: nvmem: rockchip-efuse: remove nvmem regmap dependency
[firefly-linux-kernel-4.4.55.git]
/
fs
/
overlayfs
/
copy_up.c
diff --git
a/fs/overlayfs/copy_up.c
b/fs/overlayfs/copy_up.c
index 871fcb67be9741f2aab81f3d6552306dedf4c967..eff6319d50373c05d4d829b0fd83fa784d5f187b 100644
(file)
--- a/
fs/overlayfs/copy_up.c
+++ b/
fs/overlayfs/copy_up.c
@@
-22,9
+22,9
@@
int ovl_copy_xattr(struct dentry *old, struct dentry *new)
{
int ovl_copy_xattr(struct dentry *old, struct dentry *new)
{
- ssize_t list_size, size;
- char *buf, *name, *value;
- int
error
;
+ ssize_t list_size, size
, value_size = 0
;
+ char *buf, *name, *value
= NULL
;
+ int
uninitialized_var(error)
;
if (!old->d_inode->i_op->getxattr ||
!new->d_inode->i_op->getxattr)
if (!old->d_inode->i_op->getxattr ||
!new->d_inode->i_op->getxattr)
@@
-41,29
+41,40
@@
int ovl_copy_xattr(struct dentry *old, struct dentry *new)
if (!buf)
return -ENOMEM;
if (!buf)
return -ENOMEM;
- error = -ENOMEM;
- value = kmalloc(XATTR_SIZE_MAX, GFP_KERNEL);
- if (!value)
- goto out;
-
list_size = vfs_listxattr(old, buf, list_size);
if (list_size <= 0) {
error = list_size;
list_size = vfs_listxattr(old, buf, list_size);
if (list_size <= 0) {
error = list_size;
- goto out
_free_value
;
+ goto out;
}
for (name = buf; name < (buf + list_size); name += strlen(name) + 1) {
}
for (name = buf; name < (buf + list_size); name += strlen(name) + 1) {
- size = vfs_getxattr(old, name, value, XATTR_SIZE_MAX);
- if (size <= 0) {
+retry:
+ size = vfs_getxattr(old, name, value, value_size);
+ if (size == -ERANGE)
+ size = vfs_getxattr(old, name, NULL, 0);
+
+ if (size < 0) {
error = size;
error = size;
- goto out_free_value;
+ break;
+ }
+
+ if (size > value_size) {
+ void *new;
+
+ new = krealloc(value, size, GFP_KERNEL);
+ if (!new) {
+ error = -ENOMEM;
+ break;
+ }
+ value = new;
+ value_size = size;
+ goto retry;
}
}
+
error = vfs_setxattr(new, name, value, size, 0);
if (error)
error = vfs_setxattr(new, name, value, size, 0);
if (error)
-
goto out_free_value
;
+
break
;
}
}
-
-out_free_value:
kfree(value);
out:
kfree(buf);
kfree(value);
out:
kfree(buf);
@@
-195,8
+206,7
@@
int ovl_set_attr(struct dentry *upperdentry, struct kstat *stat)
static int ovl_copy_up_locked(struct dentry *workdir, struct dentry *upperdir,
struct dentry *dentry, struct path *lowerpath,
static int ovl_copy_up_locked(struct dentry *workdir, struct dentry *upperdir,
struct dentry *dentry, struct path *lowerpath,
- struct kstat *stat, struct iattr *attr,
- const char *link)
+ struct kstat *stat, const char *link)
{
struct inode *wdir = workdir->d_inode;
struct inode *udir = upperdir->d_inode;
{
struct inode *wdir = workdir->d_inode;
struct inode *udir = upperdir->d_inode;
@@
-240,8
+250,6
@@
static int ovl_copy_up_locked(struct dentry *workdir, struct dentry *upperdir,
mutex_lock(&newdentry->d_inode->i_mutex);
err = ovl_set_attr(newdentry, stat);
mutex_lock(&newdentry->d_inode->i_mutex);
err = ovl_set_attr(newdentry, stat);
- if (!err && attr)
- err = notify_change(newdentry, attr, NULL);
mutex_unlock(&newdentry->d_inode->i_mutex);
if (err)
goto out_cleanup;
mutex_unlock(&newdentry->d_inode->i_mutex);
if (err)
goto out_cleanup;
@@
-286,8
+294,7
@@
out_cleanup:
* that point the file will have already been copied up anyway.
*/
int ovl_copy_up_one(struct dentry *parent, struct dentry *dentry,
* that point the file will have already been copied up anyway.
*/
int ovl_copy_up_one(struct dentry *parent, struct dentry *dentry,
- struct path *lowerpath, struct kstat *stat,
- struct iattr *attr)
+ struct path *lowerpath, struct kstat *stat)
{
struct dentry *workdir = ovl_workdir(dentry);
int err;
{
struct dentry *workdir = ovl_workdir(dentry);
int err;
@@
-345,26
+352,19
@@
int ovl_copy_up_one(struct dentry *parent, struct dentry *dentry,
}
upperdentry = ovl_dentry_upper(dentry);
if (upperdentry) {
}
upperdentry = ovl_dentry_upper(dentry);
if (upperdentry) {
- unlock_rename(workdir, upperdir);
+ /* Raced with another copy-up? Nothing to do, then... */
err = 0;
err = 0;
- /* Raced with another copy-up? Do the setattr here */
- if (attr) {
- mutex_lock(&upperdentry->d_inode->i_mutex);
- err = notify_change(upperdentry, attr, NULL);
- mutex_unlock(&upperdentry->d_inode->i_mutex);
- }
- goto out_put_cred;
+ goto out_unlock;
}
err = ovl_copy_up_locked(workdir, upperdir, dentry, lowerpath,
}
err = ovl_copy_up_locked(workdir, upperdir, dentry, lowerpath,
- stat,
attr,
link);
+ stat, link);
if (!err) {
/* Restore timestamps on parent (best effort) */
ovl_set_timestamps(upperdir, &pstat);
}
out_unlock:
unlock_rename(workdir, upperdir);
if (!err) {
/* Restore timestamps on parent (best effort) */
ovl_set_timestamps(upperdir, &pstat);
}
out_unlock:
unlock_rename(workdir, upperdir);
-out_put_cred:
revert_creds(old_cred);
put_cred(override_cred);
revert_creds(old_cred);
put_cred(override_cred);
@@
-406,7
+406,7
@@
int ovl_copy_up(struct dentry *dentry)
ovl_path_lower(next, &lowerpath);
err = vfs_getattr(&lowerpath, &stat);
if (!err)
ovl_path_lower(next, &lowerpath);
err = vfs_getattr(&lowerpath, &stat);
if (!err)
- err = ovl_copy_up_one(parent, next, &lowerpath, &stat
, NULL
);
+ err = ovl_copy_up_one(parent, next, &lowerpath, &stat);
dput(parent);
dput(next);
dput(parent);
dput(next);