12522fe45SThomas Gleixner // SPDX-License-Identifier: GPL-2.0-only 2e7fd4179SDavid Teigland /****************************************************************************** 3e7fd4179SDavid Teigland ******************************************************************************* 4e7fd4179SDavid Teigland ** 5e7fd4179SDavid Teigland ** Copyright (C) Sistina Software, Inc. 1997-2003 All rights reserved. 652bda2b5SDavid Teigland ** Copyright (C) 2004-2007 Red Hat, Inc. All rights reserved. 7e7fd4179SDavid Teigland ** 8e7fd4179SDavid Teigland ** 9e7fd4179SDavid Teigland ******************************************************************************* 10e7fd4179SDavid Teigland ******************************************************************************/ 11e7fd4179SDavid Teigland 12e7fd4179SDavid Teigland #include "dlm_internal.h" 136c547f26SAlexander Aring #include "midcomms.h" 143af2326cSAlexander Aring #include "lowcomms.h" 15e7fd4179SDavid Teigland #include "config.h" 16e7fd4179SDavid Teigland #include "memory.h" 1761bed0baSAlexander Aring #include "ast.h" 18e7fd4179SDavid Teigland 193af2326cSAlexander Aring static struct kmem_cache *writequeue_cache; 206c547f26SAlexander Aring static struct kmem_cache *mhandle_cache; 21e4dc81edSAlexander Aring static struct kmem_cache *msg_cache; 22e18b890bSChristoph Lameter static struct kmem_cache *lkb_cache; 233881ac04SDavid Teigland static struct kmem_cache *rsb_cache; 2461bed0baSAlexander Aring static struct kmem_cache *cb_cache; 25e7fd4179SDavid Teigland 26e7fd4179SDavid Teigland 2730727174SDenis Cheng int __init dlm_memory_init(void) 28e7fd4179SDavid Teigland { 293af2326cSAlexander Aring writequeue_cache = dlm_lowcomms_writequeue_cache_create(); 303af2326cSAlexander Aring if (!writequeue_cache) 313af2326cSAlexander Aring goto out; 323af2326cSAlexander Aring 336c547f26SAlexander Aring mhandle_cache = dlm_midcomms_cache_create(); 346c547f26SAlexander Aring if (!mhandle_cache) 353af2326cSAlexander Aring goto mhandle; 366c547f26SAlexander Aring 37e7fd4179SDavid Teigland lkb_cache = kmem_cache_create("dlm_lkb", sizeof(struct dlm_lkb), 3820c2df83SPaul Mundt __alignof__(struct dlm_lkb), 0, NULL); 39e7fd4179SDavid Teigland if (!lkb_cache) 406c547f26SAlexander Aring goto lkb; 413881ac04SDavid Teigland 42e4dc81edSAlexander Aring msg_cache = dlm_lowcomms_msg_cache_create(); 43e4dc81edSAlexander Aring if (!msg_cache) 44e4dc81edSAlexander Aring goto msg; 45e4dc81edSAlexander Aring 463881ac04SDavid Teigland rsb_cache = kmem_cache_create("dlm_rsb", sizeof(struct dlm_rsb), 473881ac04SDavid Teigland __alignof__(struct dlm_rsb), 0, NULL); 486c547f26SAlexander Aring if (!rsb_cache) 496c547f26SAlexander Aring goto rsb; 503881ac04SDavid Teigland 5161bed0baSAlexander Aring cb_cache = kmem_cache_create("dlm_cb", sizeof(struct dlm_callback), 5261bed0baSAlexander Aring __alignof__(struct dlm_callback), 0, 5361bed0baSAlexander Aring NULL); 548113aa91SYang Yingliang if (!cb_cache) 5561bed0baSAlexander Aring goto cb; 5661bed0baSAlexander Aring 5775af271eSDan Carpenter return 0; 586c547f26SAlexander Aring 5961bed0baSAlexander Aring cb: 6061bed0baSAlexander Aring kmem_cache_destroy(rsb_cache); 616c547f26SAlexander Aring rsb: 62e4dc81edSAlexander Aring kmem_cache_destroy(msg_cache); 63e4dc81edSAlexander Aring msg: 646c547f26SAlexander Aring kmem_cache_destroy(lkb_cache); 656c547f26SAlexander Aring lkb: 666c547f26SAlexander Aring kmem_cache_destroy(mhandle_cache); 673af2326cSAlexander Aring mhandle: 683af2326cSAlexander Aring kmem_cache_destroy(writequeue_cache); 696c547f26SAlexander Aring out: 706c547f26SAlexander Aring return -ENOMEM; 71e7fd4179SDavid Teigland } 72e7fd4179SDavid Teigland 73e7fd4179SDavid Teigland void dlm_memory_exit(void) 74e7fd4179SDavid Teigland { 75*89b01913SAlexander Aring rcu_barrier(); 76*89b01913SAlexander Aring 773af2326cSAlexander Aring kmem_cache_destroy(writequeue_cache); 786c547f26SAlexander Aring kmem_cache_destroy(mhandle_cache); 79e4dc81edSAlexander Aring kmem_cache_destroy(msg_cache); 80e7fd4179SDavid Teigland kmem_cache_destroy(lkb_cache); 813881ac04SDavid Teigland kmem_cache_destroy(rsb_cache); 8261bed0baSAlexander Aring kmem_cache_destroy(cb_cache); 83e7fd4179SDavid Teigland } 84e7fd4179SDavid Teigland 8552bda2b5SDavid Teigland char *dlm_allocate_lvb(struct dlm_ls *ls) 86e7fd4179SDavid Teigland { 87e7fd4179SDavid Teigland char *p; 88e7fd4179SDavid Teigland 89455597a5SAlexander Aring p = kzalloc(ls->ls_lvblen, GFP_ATOMIC); 90e7fd4179SDavid Teigland return p; 91e7fd4179SDavid Teigland } 92e7fd4179SDavid Teigland 9352bda2b5SDavid Teigland void dlm_free_lvb(char *p) 94e7fd4179SDavid Teigland { 95e7fd4179SDavid Teigland kfree(p); 96e7fd4179SDavid Teigland } 97e7fd4179SDavid Teigland 983881ac04SDavid Teigland struct dlm_rsb *dlm_allocate_rsb(struct dlm_ls *ls) 99e7fd4179SDavid Teigland { 100e7fd4179SDavid Teigland struct dlm_rsb *r; 101e7fd4179SDavid Teigland 102455597a5SAlexander Aring r = kmem_cache_zalloc(rsb_cache, GFP_ATOMIC); 103e7fd4179SDavid Teigland return r; 104e7fd4179SDavid Teigland } 105e7fd4179SDavid Teigland 10601fdeca1SAlexander Aring static void __free_rsb_rcu(struct rcu_head *rcu) 107e7fd4179SDavid Teigland { 10801fdeca1SAlexander Aring struct dlm_rsb *r = container_of(rcu, struct dlm_rsb, rcu); 109e7fd4179SDavid Teigland if (r->res_lvbptr) 11052bda2b5SDavid Teigland dlm_free_lvb(r->res_lvbptr); 1113881ac04SDavid Teigland kmem_cache_free(rsb_cache, r); 112e7fd4179SDavid Teigland } 113e7fd4179SDavid Teigland 11401fdeca1SAlexander Aring void dlm_free_rsb(struct dlm_rsb *r) 11501fdeca1SAlexander Aring { 11601fdeca1SAlexander Aring call_rcu(&r->rcu, __free_rsb_rcu); 11701fdeca1SAlexander Aring } 11801fdeca1SAlexander Aring 11952bda2b5SDavid Teigland struct dlm_lkb *dlm_allocate_lkb(struct dlm_ls *ls) 120e7fd4179SDavid Teigland { 121e7fd4179SDavid Teigland struct dlm_lkb *lkb; 122e7fd4179SDavid Teigland 123455597a5SAlexander Aring lkb = kmem_cache_zalloc(lkb_cache, GFP_ATOMIC); 124e7fd4179SDavid Teigland return lkb; 125e7fd4179SDavid Teigland } 126e7fd4179SDavid Teigland 12752bda2b5SDavid Teigland void dlm_free_lkb(struct dlm_lkb *lkb) 128e7fd4179SDavid Teigland { 1298a39dcd9SAlexander Aring if (test_bit(DLM_DFL_USER_BIT, &lkb->lkb_dflags)) { 130597d0caeSDavid Teigland struct dlm_user_args *ua; 131d292c0ccSDavid Teigland ua = lkb->lkb_ua; 132597d0caeSDavid Teigland if (ua) { 133597d0caeSDavid Teigland kfree(ua->lksb.sb_lvbptr); 134597d0caeSDavid Teigland kfree(ua); 135597d0caeSDavid Teigland } 136597d0caeSDavid Teigland } 13761bed0baSAlexander Aring 138e7fd4179SDavid Teigland kmem_cache_free(lkb_cache, lkb); 139e7fd4179SDavid Teigland } 140e7fd4179SDavid Teigland 14198808644SAlexander Aring struct dlm_mhandle *dlm_allocate_mhandle(void) 1426c547f26SAlexander Aring { 14398808644SAlexander Aring return kmem_cache_alloc(mhandle_cache, GFP_ATOMIC); 1446c547f26SAlexander Aring } 1456c547f26SAlexander Aring 1466c547f26SAlexander Aring void dlm_free_mhandle(struct dlm_mhandle *mhandle) 1476c547f26SAlexander Aring { 1486c547f26SAlexander Aring kmem_cache_free(mhandle_cache, mhandle); 1496c547f26SAlexander Aring } 1503af2326cSAlexander Aring 1513af2326cSAlexander Aring struct writequeue_entry *dlm_allocate_writequeue(void) 1523af2326cSAlexander Aring { 1533af2326cSAlexander Aring return kmem_cache_alloc(writequeue_cache, GFP_ATOMIC); 1543af2326cSAlexander Aring } 1553af2326cSAlexander Aring 1563af2326cSAlexander Aring void dlm_free_writequeue(struct writequeue_entry *writequeue) 1573af2326cSAlexander Aring { 1583af2326cSAlexander Aring kmem_cache_free(writequeue_cache, writequeue); 1593af2326cSAlexander Aring } 160e4dc81edSAlexander Aring 16198808644SAlexander Aring struct dlm_msg *dlm_allocate_msg(void) 162e4dc81edSAlexander Aring { 16398808644SAlexander Aring return kmem_cache_alloc(msg_cache, GFP_ATOMIC); 164e4dc81edSAlexander Aring } 165e4dc81edSAlexander Aring 166e4dc81edSAlexander Aring void dlm_free_msg(struct dlm_msg *msg) 167e4dc81edSAlexander Aring { 168e4dc81edSAlexander Aring kmem_cache_free(msg_cache, msg); 169e4dc81edSAlexander Aring } 17061bed0baSAlexander Aring 17161bed0baSAlexander Aring struct dlm_callback *dlm_allocate_cb(void) 17261bed0baSAlexander Aring { 17361bed0baSAlexander Aring return kmem_cache_alloc(cb_cache, GFP_ATOMIC); 17461bed0baSAlexander Aring } 17561bed0baSAlexander Aring 17661bed0baSAlexander Aring void dlm_free_cb(struct dlm_callback *cb) 17761bed0baSAlexander Aring { 17861bed0baSAlexander Aring kmem_cache_free(cb_cache, cb); 17961bed0baSAlexander Aring } 180