struct ldlm_lock's l_lvb_data field is freed in ldlm_lock_put()
using OBD_FREE. However, some other code paths can attach
a buffer to l_lvb_data that was allocated using OBD_ALLOC_LARGE.
This can lead to a kfree() of a vmalloc()ed buffer, which can
trigger a kernel Oops.
Change-Id: Ic75a67530862eeb4d065c14bbbac80939bff5731
Signed-off-by: Christopher J. Morrone <morrone2@llnl.gov>
Reviewed-on: http://review.whamcloud.com/8298
Tested-by: Jenkins
Reviewed-by: Andreas Dilger <andreas.dilger@intel.com>
Reviewed-by: Faccini Bruno <bruno.faccini@intel.com>
Tested-by: Maloo <hpdd-maloo@intel.com>
}
if (lock->l_lvb_data != NULL)
- OBD_FREE(lock->l_lvb_data, lock->l_lvb_len);
+ OBD_FREE_LARGE(lock->l_lvb_data, lock->l_lvb_len);
ldlm_interval_free(ldlm_interval_detach(lock));
lu_ref_fini(&lock->l_reference);
if (lvb_len) {
lock->l_lvb_len = lvb_len;
- OBD_ALLOC(lock->l_lvb_data, lvb_len);
+ OBD_ALLOC_LARGE(lock->l_lvb_data, lvb_len);
if (lock->l_lvb_data == NULL)
GOTO(out, 0);
}
* variable length */
void *lvb_data;
- OBD_ALLOC(lvb_data, lvb_len);
+ OBD_ALLOC_LARGE(lvb_data, lvb_len);
if (lvb_data == NULL) {
LDLM_ERROR(lock, "No memory: %d.\n", lvb_len);
GOTO(out, rc = -ENOMEM);