Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-or-later
0002 /*
0003  *   Copyright (C) 2019 Samsung Electronics Co., Ltd.
0004  */
0005 
0006 #include <linux/list.h>
0007 #include <linux/mm.h>
0008 #include <linux/slab.h>
0009 #include <linux/workqueue.h>
0010 
0011 #include "server.h"
0012 #include "connection.h"
0013 #include "ksmbd_work.h"
0014 #include "mgmt/ksmbd_ida.h"
0015 
0016 static struct kmem_cache *work_cache;
0017 static struct workqueue_struct *ksmbd_wq;
0018 
0019 struct ksmbd_work *ksmbd_alloc_work_struct(void)
0020 {
0021     struct ksmbd_work *work = kmem_cache_zalloc(work_cache, GFP_KERNEL);
0022 
0023     if (work) {
0024         work->compound_fid = KSMBD_NO_FID;
0025         work->compound_pfid = KSMBD_NO_FID;
0026         INIT_LIST_HEAD(&work->request_entry);
0027         INIT_LIST_HEAD(&work->async_request_entry);
0028         INIT_LIST_HEAD(&work->fp_entry);
0029         INIT_LIST_HEAD(&work->interim_entry);
0030     }
0031     return work;
0032 }
0033 
0034 void ksmbd_free_work_struct(struct ksmbd_work *work)
0035 {
0036     WARN_ON(work->saved_cred != NULL);
0037 
0038     kvfree(work->response_buf);
0039     kvfree(work->aux_payload_buf);
0040     kfree(work->tr_buf);
0041     kvfree(work->request_buf);
0042     if (work->async_id)
0043         ksmbd_release_id(&work->conn->async_ida, work->async_id);
0044     kmem_cache_free(work_cache, work);
0045 }
0046 
0047 void ksmbd_work_pool_destroy(void)
0048 {
0049     kmem_cache_destroy(work_cache);
0050 }
0051 
0052 int ksmbd_work_pool_init(void)
0053 {
0054     work_cache = kmem_cache_create("ksmbd_work_cache",
0055                        sizeof(struct ksmbd_work), 0,
0056                        SLAB_HWCACHE_ALIGN, NULL);
0057     if (!work_cache)
0058         return -ENOMEM;
0059     return 0;
0060 }
0061 
0062 int ksmbd_workqueue_init(void)
0063 {
0064     ksmbd_wq = alloc_workqueue("ksmbd-io", 0, 0);
0065     if (!ksmbd_wq)
0066         return -ENOMEM;
0067     return 0;
0068 }
0069 
0070 void ksmbd_workqueue_destroy(void)
0071 {
0072     destroy_workqueue(ksmbd_wq);
0073     ksmbd_wq = NULL;
0074 }
0075 
0076 bool ksmbd_queue_work(struct ksmbd_work *work)
0077 {
0078     return queue_work(ksmbd_wq, &work->work);
0079 }