1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright (C) 2016 Intel Corporation. 3 * All rights reserved. 4 */ 5 6 #include "bdev_aio.h" 7 #include "spdk/rpc.h" 8 #include "spdk/util.h" 9 #include "spdk/string.h" 10 #include "spdk/log.h" 11 12 struct rpc_construct_aio { 13 char *name; 14 char *filename; 15 uint32_t block_size; 16 bool readonly; 17 bool fallocate; 18 }; 19 20 struct rpc_construct_aio_ctx { 21 struct rpc_construct_aio req; 22 struct spdk_jsonrpc_request *request; 23 }; 24 25 static void 26 free_rpc_construct_aio(struct rpc_construct_aio_ctx *ctx) 27 { 28 free(ctx->req.name); 29 free(ctx->req.filename); 30 free(ctx); 31 } 32 33 static const struct spdk_json_object_decoder rpc_construct_aio_decoders[] = { 34 {"name", offsetof(struct rpc_construct_aio, name), spdk_json_decode_string}, 35 {"filename", offsetof(struct rpc_construct_aio, filename), spdk_json_decode_string}, 36 {"block_size", offsetof(struct rpc_construct_aio, block_size), spdk_json_decode_uint32, true}, 37 {"readonly", offsetof(struct rpc_construct_aio, readonly), spdk_json_decode_bool, true}, 38 {"fallocate", offsetof(struct rpc_construct_aio, fallocate), spdk_json_decode_bool, true}, 39 }; 40 41 static void 42 rpc_bdev_aio_create_cb(void *cb_arg) 43 { 44 struct rpc_construct_aio_ctx *ctx = cb_arg; 45 struct spdk_jsonrpc_request *request = ctx->request; 46 struct spdk_json_write_ctx *w; 47 48 w = spdk_jsonrpc_begin_result(request); 49 spdk_json_write_string(w, ctx->req.name); 50 spdk_jsonrpc_end_result(request, w); 51 free_rpc_construct_aio(ctx); 52 } 53 54 static void 55 rpc_bdev_aio_create(struct spdk_jsonrpc_request *request, 56 const struct spdk_json_val *params) 57 { 58 struct rpc_construct_aio_ctx *ctx; 59 int rc; 60 61 ctx = calloc(1, sizeof(*ctx)); 62 if (!ctx) { 63 spdk_jsonrpc_send_error_response(request, -ENOMEM, spdk_strerror(ENOMEM)); 64 return; 65 } 66 67 if (spdk_json_decode_object(params, rpc_construct_aio_decoders, 68 SPDK_COUNTOF(rpc_construct_aio_decoders), 69 &ctx->req)) { 70 SPDK_ERRLOG("spdk_json_decode_object failed\n"); 71 spdk_jsonrpc_send_error_response(request, SPDK_JSONRPC_ERROR_INTERNAL_ERROR, 72 "spdk_json_decode_object failed"); 73 free_rpc_construct_aio(ctx); 74 return; 75 } 76 77 ctx->request = request; 78 rc = create_aio_bdev(ctx->req.name, ctx->req.filename, ctx->req.block_size, 79 ctx->req.readonly, ctx->req.fallocate); 80 if (rc) { 81 spdk_jsonrpc_send_error_response(request, rc, spdk_strerror(-rc)); 82 free_rpc_construct_aio(ctx); 83 return; 84 } 85 86 spdk_bdev_wait_for_examine(rpc_bdev_aio_create_cb, ctx); 87 } 88 SPDK_RPC_REGISTER("bdev_aio_create", rpc_bdev_aio_create, SPDK_RPC_RUNTIME) 89 90 struct rpc_rescan_aio { 91 char *name; 92 }; 93 94 static const struct spdk_json_object_decoder rpc_rescan_aio_decoders[] = { 95 {"name", offsetof(struct rpc_rescan_aio, name), spdk_json_decode_string}, 96 }; 97 98 static void 99 rpc_bdev_aio_rescan(struct spdk_jsonrpc_request *request, 100 const struct spdk_json_val *params) 101 { 102 struct rpc_rescan_aio req = {NULL}; 103 int bdeverrno; 104 105 if (spdk_json_decode_object(params, rpc_rescan_aio_decoders, 106 SPDK_COUNTOF(rpc_rescan_aio_decoders), 107 &req)) { 108 spdk_jsonrpc_send_error_response(request, SPDK_JSONRPC_ERROR_INTERNAL_ERROR, 109 "spdk_json_decode_object failed"); 110 goto cleanup; 111 } 112 113 bdeverrno = bdev_aio_rescan(req.name); 114 if (bdeverrno) { 115 spdk_jsonrpc_send_error_response(request, bdeverrno, 116 spdk_strerror(-bdeverrno)); 117 goto cleanup; 118 } 119 120 spdk_jsonrpc_send_bool_response(request, true); 121 cleanup: 122 free(req.name); 123 } 124 SPDK_RPC_REGISTER("bdev_aio_rescan", rpc_bdev_aio_rescan, SPDK_RPC_RUNTIME) 125 126 struct rpc_delete_aio { 127 char *name; 128 }; 129 130 static void 131 free_rpc_delete_aio(struct rpc_delete_aio *r) 132 { 133 free(r->name); 134 } 135 136 static const struct spdk_json_object_decoder rpc_delete_aio_decoders[] = { 137 {"name", offsetof(struct rpc_delete_aio, name), spdk_json_decode_string}, 138 }; 139 140 static void 141 _rpc_bdev_aio_delete_cb(void *cb_arg, int bdeverrno) 142 { 143 struct spdk_jsonrpc_request *request = cb_arg; 144 145 if (bdeverrno == 0) { 146 spdk_jsonrpc_send_bool_response(request, true); 147 } else { 148 spdk_jsonrpc_send_error_response(request, bdeverrno, spdk_strerror(-bdeverrno)); 149 } 150 } 151 152 static void 153 rpc_bdev_aio_delete(struct spdk_jsonrpc_request *request, 154 const struct spdk_json_val *params) 155 { 156 struct rpc_delete_aio req = {NULL}; 157 158 if (spdk_json_decode_object(params, rpc_delete_aio_decoders, 159 SPDK_COUNTOF(rpc_delete_aio_decoders), 160 &req)) { 161 spdk_jsonrpc_send_error_response(request, SPDK_JSONRPC_ERROR_INTERNAL_ERROR, 162 "spdk_json_decode_object failed"); 163 goto cleanup; 164 } 165 166 bdev_aio_delete(req.name, _rpc_bdev_aio_delete_cb, request); 167 168 cleanup: 169 free_rpc_delete_aio(&req); 170 } 171 SPDK_RPC_REGISTER("bdev_aio_delete", rpc_bdev_aio_delete, SPDK_RPC_RUNTIME) 172