[Cluster-devel] [PATCH] dlm: fixed memory leaks after failed ls_remove_names allocation

2018-11-15 Thread Vasily Averin
If allocation fails on last elements of array need to free already
allocated elements.

Fixes 789924ba635f ("dlm: fix race between remove and lookup")
Cc: sta...@kernel.org # 3.6

Signed-off-by: Vasily Averin 
---
 fs/dlm/lockspace.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/fs/dlm/lockspace.c b/fs/dlm/lockspace.c
index 5ba94be006ee..f99e110a0af8 100644
--- a/fs/dlm/lockspace.c
+++ b/fs/dlm/lockspace.c
@@ -532,7 +532,7 @@ static int new_lockspace(const char *name, const char 
*cluster,
ls->ls_remove_names[i] = kzalloc(DLM_RESNAME_MAXLEN+1,
 GFP_KERNEL);
if (!ls->ls_remove_names[i])
-   goto out_rsbtbl;
+   goto out_remove_names;
}
 
idr_init(&ls->ls_lkbidr);
@@ -680,6 +680,7 @@ static int new_lockspace(const char *name, const char 
*cluster,
kfree(ls->ls_recover_buf);
  out_lkbidr:
idr_destroy(&ls->ls_lkbidr);
+ out_remove_names:
for (i = 0; i < DLM_REMOVE_NAMES_MAX; i++) {
if (ls->ls_remove_names[i])
kfree(ls->ls_remove_names[i]);
-- 
2.17.1



[Cluster-devel] lost idr_destroy for ls_recover_idr in release_lockspace() ?

2018-11-15 Thread Vasily Averin
Dear David,
I've noticed that release_lockspace() lacks idr_destroy(&ls->ls_recover_idr),
though it is called on rollback in new_lockspace().

It seems for me it is not critical, and should not lead to any leaks,
however could you please re-check it?

Thank you,
    Vasily Averin



[Cluster-devel] [PATCH 3/3] dlm: memory leaks on error path in dlm_user_request()

2018-11-15 Thread Vasily Averin
According to comment in dlm_user_request() ua should be freed
in dlm_free_lkb() after successful attach to lkb.

However ua is attached to lkb not in set_lock_args() but later,
inside request_lock().

Fixes 597d0cae0f99 ("[DLM] dlm: user locks")
Cc: sta...@kernel.org # 2.6.19

Signed-off-by: Vasily Averin 
---
 fs/dlm/lock.c | 14 +++---
 1 file changed, 7 insertions(+), 7 deletions(-)

diff --git a/fs/dlm/lock.c b/fs/dlm/lock.c
index 03d767b94f7b..a928ba008d7d 100644
--- a/fs/dlm/lock.c
+++ b/fs/dlm/lock.c
@@ -5795,20 +5795,20 @@ int dlm_user_request(struct dlm_ls *ls, struct 
dlm_user_args *ua,
goto out;
}
}
-
-   /* After ua is attached to lkb it will be freed by dlm_free_lkb().
-  When DLM_IFL_USER is set, the dlm knows that this is a userspace
-  lock and that lkb_astparam is the dlm_user_args structure. */
-
error = set_lock_args(mode, &ua->lksb, flags, namelen, timeout_cs,
  fake_astfn, ua, fake_bastfn, &args);
-   lkb->lkb_flags |= DLM_IFL_USER;
-
if (error) {
+   kfree(ua->lksb.sb_lvbptr);
+   ua->lksb.sb_lvbptr = NULL;
+   kfree(ua);
__put_lkb(ls, lkb);
goto out;
}
 
+   /* After ua is attached to lkb it will be freed by dlm_free_lkb().
+  When DLM_IFL_USER is set, the dlm knows that this is a userspace
+  lock and that lkb_astparam is the dlm_user_args structure. */
+   lkb->lkb_flags |= DLM_IFL_USER;
error = request_lock(ls, lkb, name, namelen, &args);
 
switch (error) {
-- 
2.17.1



[Cluster-devel] [PATCH v2] dlm: fixed memory leaks after failed ls_remove_names allocation

2018-11-15 Thread Vasily Averin
If allocation fails on last elements of array need to free already
allocated elements.

v2: just move existing out_rsbtbl label to right place

Fixes 789924ba635f ("dlm: fix race between remove and lookup")
Cc: sta...@kernel.org # 3.6

Signed-off-by: Vasily Averin 
---
 fs/dlm/lockspace.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/fs/dlm/lockspace.c b/fs/dlm/lockspace.c
index 5ba94be006ee..6a1529e478f3 100644
--- a/fs/dlm/lockspace.c
+++ b/fs/dlm/lockspace.c
@@ -680,11 +680,11 @@ static int new_lockspace(const char *name, const char 
*cluster,
kfree(ls->ls_recover_buf);
  out_lkbidr:
idr_destroy(&ls->ls_lkbidr);
+ out_rsbtbl:
for (i = 0; i < DLM_REMOVE_NAMES_MAX; i++) {
if (ls->ls_remove_names[i])
kfree(ls->ls_remove_names[i]);
}
- out_rsbtbl:
vfree(ls->ls_rsbtbl);
  out_lsfree:
if (do_unreg)
-- 
2.17.1



[Cluster-devel] [PATCH 2/3] dlm: lost put_lkb on error path in receive_convert() and receive_unlock()

2018-11-15 Thread Vasily Averin
Fixes 6d40c4a708e0 ("dlm: improve error and debug messages")
Cc: sta...@kernel.org # 3.5

Signed-off-by: Vasily Averin 
---
 fs/dlm/lock.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/fs/dlm/lock.c b/fs/dlm/lock.c
index 2cb125cc21c9..03d767b94f7b 100644
--- a/fs/dlm/lock.c
+++ b/fs/dlm/lock.c
@@ -4180,6 +4180,7 @@ static int receive_convert(struct dlm_ls *ls, struct 
dlm_message *ms)
  (unsigned long long)lkb->lkb_recover_seq,
  ms->m_header.h_nodeid, ms->m_lkid);
error = -ENOENT;
+   dlm_put_lkb(lkb);
goto fail;
}
 
@@ -4233,6 +4234,7 @@ static int receive_unlock(struct dlm_ls *ls, struct 
dlm_message *ms)
  lkb->lkb_id, lkb->lkb_remid,
  ms->m_header.h_nodeid, ms->m_lkid);
error = -ENOENT;
+   dlm_put_lkb(lkb);
goto fail;
}
 
-- 
2.17.1



[Cluster-devel] [PATCH 1/3] dlm: possible memory leak on error path in create_lkb()

2018-11-15 Thread Vasily Averin
Fixes 3d6aa675fff9 ("dlm: keep lkbs in idr")
Cc: sta...@kernel.org # 3.1

Signed-off-by: Vasily Averin 
---
 fs/dlm/lock.c | 1 +
 1 file changed, 1 insertion(+)

diff --git a/fs/dlm/lock.c b/fs/dlm/lock.c
index cc91963683de..2cb125cc21c9 100644
--- a/fs/dlm/lock.c
+++ b/fs/dlm/lock.c
@@ -1209,6 +1209,7 @@ static int create_lkb(struct dlm_ls *ls, struct dlm_lkb 
**lkb_ret)
 
if (rv < 0) {
log_error(ls, "create_lkb idr error %d", rv);
+   dlm_free_lkb(lkb);
return rv;
}
 
-- 
2.17.1



[Cluster-devel] [PATCH 0/1] dlm: seq_file .next functions should increase position index

2020-01-23 Thread Vasily Averin
In Aug 2018 NeilBrown noticed 
commit 1f4aace60b0e ("fs/seq_file.c: simplify seq_file iteration code and 
interface")
"Some ->next functions do not increment *pos when they return NULL...
Note that such ->next functions are buggy and should be fixed. 
A simple demonstration is
   
dd if=/proc/swaps bs=1000 skip=1

Choose any block size larger than the size of /proc/swaps.  This will
always show the whole last line of /proc/swaps"

Described problem is still actual. If you make lseek into middle of last output 
line 
following read will output end of last line and whole last line once again.

$ dd if=/proc/swaps bs=1  # usual output
FilenameTypeSizeUsedPriority
/dev/dm-0   partition   4194812 97536   -2
104+0 records in
104+0 records out
104 bytes copied

$ dd if=/proc/swaps bs=40 skip=1# last line was generated twice
dd: /proc/swaps: cannot skip to specified offset
v/dm-0   partition  4194812 97536   -2
/dev/dm-0   partition   4194812 97536   -2 
3+1 records in
3+1 records out
131 bytes copied

There are lot of other affected files, I've found 30+ including
/proc/net/ip_tables_matches and /proc/sysvipc/*

Following patch fixes the problem in dlm-related file

https://bugzilla.kernel.org/show_bug.cgi?id=206283

Vasily Averin (1):
  table_seq_next should increase position index

 fs/dlm/debug_fs.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

-- 
1.8.3.1




[Cluster-devel] [PATCH 1/1] table_seq_next should increase position index

2020-01-23 Thread Vasily Averin
if seq_file .next fuction does not change position index,
read after some lseek can generate unexpected output.

https://bugzilla.kernel.org/show_bug.cgi?id=206283
Signed-off-by: Vasily Averin 
---
 fs/dlm/debug_fs.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/fs/dlm/debug_fs.c b/fs/dlm/debug_fs.c
index d6bbccb..c1eda93 100644
--- a/fs/dlm/debug_fs.c
+++ b/fs/dlm/debug_fs.c
@@ -523,7 +523,7 @@ static void *table_seq_next(struct seq_file *seq, void 
*iter_ptr, loff_t *pos)
ri->rsb = r;
spin_unlock(&ls->ls_rsbtbl[bucket].lock);
dlm_put_rsb(rp);
-   ++*pos;
+   ++(*pos);
return ri;
}
spin_unlock(&ls->ls_rsbtbl[bucket].lock);
@@ -542,6 +542,7 @@ static void *table_seq_next(struct seq_file *seq, void 
*iter_ptr, loff_t *pos)
 
if (bucket >= ls->ls_rsbtbl_size) {
kfree(ri);
+   ++(*pos);
return NULL;
}
tree = toss ? &ls->ls_rsbtbl[bucket].toss : 
&ls->ls_rsbtbl[bucket].keep;
-- 
1.8.3.1




Re: [Cluster-devel] [PATCH 1/1] table_seq_next should increase position index

2020-02-25 Thread Vasily Averin
Could I get any comments?

Unfortunately I do not have enough experience with dlm and cannot verify the 
patch locally

Usually you can observe following related problems:
- read after lseek beyond end of file, described by NeilBrown in  
 commit 1f4aace60b0e ("fs/seq_file.c: simplify seq_file iteration code and 
interface")
 "dd if= bs=1000 skip=1" will incorrectly generate whole last 
line

- read after lseek on into middle of last line will output expected rest of
 last line but then repeat whole last line once again. 

- If .show() function generates multi-line output following bash script will 
never finish.

 $ q=;while read -r r;do echo "$((++q)) $r";done < AFFECTED_FILE

Thank you,
Vasily Averin

On 1/24/20 9:03 AM, Vasily Averin wrote:
> if seq_file .next fuction does not change position index,
> read after some lseek can generate unexpected output.
> 
> https://bugzilla.kernel.org/show_bug.cgi?id=206283
> Signed-off-by: Vasily Averin 
> ---
>  fs/dlm/debug_fs.c | 3 ++-
>  1 file changed, 2 insertions(+), 1 deletion(-)
> 
> diff --git a/fs/dlm/debug_fs.c b/fs/dlm/debug_fs.c
> index d6bbccb..c1eda93 100644
> --- a/fs/dlm/debug_fs.c
> +++ b/fs/dlm/debug_fs.c
> @@ -523,7 +523,7 @@ static void *table_seq_next(struct seq_file *seq, void 
> *iter_ptr, loff_t *pos)
>   ri->rsb = r;
>   spin_unlock(&ls->ls_rsbtbl[bucket].lock);
>   dlm_put_rsb(rp);
> - ++*pos;
> + ++(*pos);
>   return ri;
>   }
>   spin_unlock(&ls->ls_rsbtbl[bucket].lock);
> @@ -542,6 +542,7 @@ static void *table_seq_next(struct seq_file *seq, void 
> *iter_ptr, loff_t *pos)
>  
>   if (bucket >= ls->ls_rsbtbl_size) {
>   kfree(ri);
> + ++(*pos);
>   return NULL;
>   }
>   tree = toss ? &ls->ls_rsbtbl[bucket].toss : 
> &ls->ls_rsbtbl[bucket].keep;
>