rxperf.c 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703
  1. // SPDX-License-Identifier: GPL-2.0-or-later
  2. /* In-kernel rxperf server for testing purposes.
  3. *
  4. * Copyright (C) 2022 Red Hat, Inc. All Rights Reserved.
  5. * Written by David Howells (dhowells@redhat.com)
  6. */
  7. #define pr_fmt(fmt) "rxperf: " fmt
  8. #include <linux/module.h>
  9. #include <linux/slab.h>
  10. #include <crypto/krb5.h>
  11. #include <net/sock.h>
  12. #include <net/af_rxrpc.h>
  13. #define RXRPC_TRACE_ONLY_DEFINE_ENUMS
  14. #include <trace/events/rxrpc.h>
  15. MODULE_DESCRIPTION("rxperf test server (afs)");
  16. MODULE_AUTHOR("Red Hat, Inc.");
  17. MODULE_LICENSE("GPL");
  18. #define RXPERF_PORT 7009
  19. #define RX_PERF_SERVICE 147
  20. #define RX_PERF_VERSION 3
  21. #define RX_PERF_SEND 0
  22. #define RX_PERF_RECV 1
  23. #define RX_PERF_RPC 3
  24. #define RX_PERF_FILE 4
  25. #define RX_PERF_MAGIC_COOKIE 0x4711
  26. struct rxperf_proto_params {
  27. __be32 version;
  28. __be32 type;
  29. __be32 rsize;
  30. __be32 wsize;
  31. } __packed;
  32. static const u8 rxperf_magic_cookie[] = { 0x00, 0x00, 0x47, 0x11 };
  33. static const u8 secret[8] = { 0xa7, 0x83, 0x8a, 0xcb, 0xc7, 0x83, 0xec, 0x94 };
  34. enum rxperf_call_state {
  35. RXPERF_CALL_SV_AWAIT_PARAMS, /* Server: Awaiting parameter block */
  36. RXPERF_CALL_SV_AWAIT_REQUEST, /* Server: Awaiting request data */
  37. RXPERF_CALL_SV_REPLYING, /* Server: Replying */
  38. RXPERF_CALL_SV_AWAIT_ACK, /* Server: Awaiting final ACK */
  39. RXPERF_CALL_COMPLETE, /* Completed or failed */
  40. };
  41. struct rxperf_call {
  42. struct rxrpc_call *rxcall;
  43. struct iov_iter iter;
  44. struct kvec kvec[1];
  45. struct work_struct work;
  46. const char *type;
  47. size_t iov_len;
  48. size_t req_len; /* Size of request blob */
  49. size_t reply_len; /* Size of reply blob */
  50. unsigned int debug_id;
  51. unsigned int operation_id;
  52. struct rxperf_proto_params params;
  53. __be32 tmp[2];
  54. s32 abort_code;
  55. enum rxperf_call_state state;
  56. short error;
  57. unsigned short unmarshal;
  58. u16 service_id;
  59. int (*deliver)(struct rxperf_call *call);
  60. void (*processor)(struct work_struct *work);
  61. };
  62. static struct socket *rxperf_socket;
  63. static struct key *rxperf_sec_keyring; /* Ring of security/crypto keys */
  64. static struct workqueue_struct *rxperf_workqueue;
  65. static void rxperf_deliver_to_call(struct work_struct *work);
  66. static int rxperf_deliver_param_block(struct rxperf_call *call);
  67. static int rxperf_deliver_request(struct rxperf_call *call);
  68. static int rxperf_process_call(struct rxperf_call *call);
  69. static void rxperf_charge_preallocation(struct work_struct *work);
  70. static DECLARE_WORK(rxperf_charge_preallocation_work,
  71. rxperf_charge_preallocation);
  72. static inline void rxperf_set_call_state(struct rxperf_call *call,
  73. enum rxperf_call_state to)
  74. {
  75. call->state = to;
  76. }
  77. static inline void rxperf_set_call_complete(struct rxperf_call *call,
  78. int error, s32 remote_abort)
  79. {
  80. if (call->state != RXPERF_CALL_COMPLETE) {
  81. call->abort_code = remote_abort;
  82. call->error = error;
  83. call->state = RXPERF_CALL_COMPLETE;
  84. }
  85. }
  86. static void rxperf_rx_discard_new_call(struct rxrpc_call *rxcall,
  87. unsigned long user_call_ID)
  88. {
  89. kfree((struct rxperf_call *)user_call_ID);
  90. }
  91. static void rxperf_rx_new_call(struct sock *sk, struct rxrpc_call *rxcall,
  92. unsigned long user_call_ID)
  93. {
  94. queue_work(rxperf_workqueue, &rxperf_charge_preallocation_work);
  95. }
  96. static void rxperf_queue_call_work(struct rxperf_call *call)
  97. {
  98. queue_work(rxperf_workqueue, &call->work);
  99. }
  100. static void rxperf_notify_rx(struct sock *sk, struct rxrpc_call *rxcall,
  101. unsigned long call_user_ID)
  102. {
  103. struct rxperf_call *call = (struct rxperf_call *)call_user_ID;
  104. if (call->state != RXPERF_CALL_COMPLETE)
  105. rxperf_queue_call_work(call);
  106. }
  107. static void rxperf_rx_attach(struct rxrpc_call *rxcall, unsigned long user_call_ID)
  108. {
  109. struct rxperf_call *call = (struct rxperf_call *)user_call_ID;
  110. call->rxcall = rxcall;
  111. }
  112. static void rxperf_notify_end_reply_tx(struct sock *sock,
  113. struct rxrpc_call *rxcall,
  114. unsigned long call_user_ID)
  115. {
  116. rxperf_set_call_state((struct rxperf_call *)call_user_ID,
  117. RXPERF_CALL_SV_AWAIT_ACK);
  118. }
  119. static const struct rxrpc_kernel_ops rxperf_rxrpc_callback_ops = {
  120. .notify_new_call = rxperf_rx_new_call,
  121. .discard_new_call = rxperf_rx_discard_new_call,
  122. .user_attach_call = rxperf_rx_attach,
  123. };
  124. /*
  125. * Charge the incoming call preallocation.
  126. */
  127. static void rxperf_charge_preallocation(struct work_struct *work)
  128. {
  129. struct rxperf_call *call;
  130. for (;;) {
  131. call = kzalloc_obj(*call);
  132. if (!call)
  133. break;
  134. call->type = "unset";
  135. call->debug_id = atomic_inc_return(&rxrpc_debug_id);
  136. call->deliver = rxperf_deliver_param_block;
  137. call->state = RXPERF_CALL_SV_AWAIT_PARAMS;
  138. call->service_id = RX_PERF_SERVICE;
  139. call->iov_len = sizeof(call->params);
  140. call->kvec[0].iov_len = sizeof(call->params);
  141. call->kvec[0].iov_base = &call->params;
  142. iov_iter_kvec(&call->iter, READ, call->kvec, 1, call->iov_len);
  143. INIT_WORK(&call->work, rxperf_deliver_to_call);
  144. if (rxrpc_kernel_charge_accept(rxperf_socket,
  145. rxperf_notify_rx,
  146. (unsigned long)call,
  147. GFP_KERNEL,
  148. call->debug_id) < 0)
  149. break;
  150. call = NULL;
  151. }
  152. kfree(call);
  153. }
  154. /*
  155. * Open an rxrpc socket and bind it to be a server for callback notifications
  156. * - the socket is left in blocking mode and non-blocking ops use MSG_DONTWAIT
  157. */
  158. static int rxperf_open_socket(void)
  159. {
  160. struct sockaddr_rxrpc srx;
  161. struct socket *socket;
  162. int ret;
  163. ret = sock_create_kern(&init_net, AF_RXRPC, SOCK_DGRAM, PF_INET6,
  164. &socket);
  165. if (ret < 0)
  166. goto error_1;
  167. socket->sk->sk_allocation = GFP_NOFS;
  168. /* bind the callback manager's address to make this a server socket */
  169. memset(&srx, 0, sizeof(srx));
  170. srx.srx_family = AF_RXRPC;
  171. srx.srx_service = RX_PERF_SERVICE;
  172. srx.transport_type = SOCK_DGRAM;
  173. srx.transport_len = sizeof(srx.transport.sin6);
  174. srx.transport.sin6.sin6_family = AF_INET6;
  175. srx.transport.sin6.sin6_port = htons(RXPERF_PORT);
  176. ret = rxrpc_sock_set_min_security_level(socket->sk,
  177. RXRPC_SECURITY_ENCRYPT);
  178. if (ret < 0)
  179. goto error_2;
  180. ret = rxrpc_sock_set_security_keyring(socket->sk, rxperf_sec_keyring);
  181. ret = kernel_bind(socket, (struct sockaddr_unsized *)&srx, sizeof(srx));
  182. if (ret < 0)
  183. goto error_2;
  184. rxrpc_kernel_set_notifications(socket, &rxperf_rxrpc_callback_ops);
  185. ret = kernel_listen(socket, INT_MAX);
  186. if (ret < 0)
  187. goto error_2;
  188. rxperf_socket = socket;
  189. rxperf_charge_preallocation(&rxperf_charge_preallocation_work);
  190. return 0;
  191. error_2:
  192. sock_release(socket);
  193. error_1:
  194. pr_err("Can't set up rxperf socket: %d\n", ret);
  195. return ret;
  196. }
  197. /*
  198. * close the rxrpc socket rxperf was using
  199. */
  200. static void rxperf_close_socket(void)
  201. {
  202. kernel_listen(rxperf_socket, 0);
  203. kernel_sock_shutdown(rxperf_socket, SHUT_RDWR);
  204. flush_workqueue(rxperf_workqueue);
  205. sock_release(rxperf_socket);
  206. }
  207. /*
  208. * Log remote abort codes that indicate that we have a protocol disagreement
  209. * with the server.
  210. */
  211. static void rxperf_log_error(struct rxperf_call *call, s32 remote_abort)
  212. {
  213. static int max = 0;
  214. const char *msg;
  215. int m;
  216. switch (remote_abort) {
  217. case RX_EOF: msg = "unexpected EOF"; break;
  218. case RXGEN_CC_MARSHAL: msg = "client marshalling"; break;
  219. case RXGEN_CC_UNMARSHAL: msg = "client unmarshalling"; break;
  220. case RXGEN_SS_MARSHAL: msg = "server marshalling"; break;
  221. case RXGEN_SS_UNMARSHAL: msg = "server unmarshalling"; break;
  222. case RXGEN_DECODE: msg = "opcode decode"; break;
  223. case RXGEN_SS_XDRFREE: msg = "server XDR cleanup"; break;
  224. case RXGEN_CC_XDRFREE: msg = "client XDR cleanup"; break;
  225. case -32: msg = "insufficient data"; break;
  226. default:
  227. return;
  228. }
  229. m = max;
  230. if (m < 3) {
  231. max = m + 1;
  232. pr_info("Peer reported %s failure on %s\n", msg, call->type);
  233. }
  234. }
  235. /*
  236. * deliver messages to a call
  237. */
  238. static void rxperf_deliver_to_call(struct work_struct *work)
  239. {
  240. struct rxperf_call *call = container_of(work, struct rxperf_call, work);
  241. enum rxperf_call_state state;
  242. u32 abort_code, remote_abort = 0;
  243. int ret = 0;
  244. if (call->state == RXPERF_CALL_COMPLETE)
  245. return;
  246. while (state = call->state,
  247. state == RXPERF_CALL_SV_AWAIT_PARAMS ||
  248. state == RXPERF_CALL_SV_AWAIT_REQUEST ||
  249. state == RXPERF_CALL_SV_AWAIT_ACK
  250. ) {
  251. if (state == RXPERF_CALL_SV_AWAIT_ACK) {
  252. if (!rxrpc_kernel_check_life(rxperf_socket, call->rxcall))
  253. goto call_complete;
  254. return;
  255. }
  256. ret = call->deliver(call);
  257. if (ret == 0)
  258. ret = rxperf_process_call(call);
  259. switch (ret) {
  260. case 0:
  261. continue;
  262. case -EINPROGRESS:
  263. case -EAGAIN:
  264. return;
  265. case -ECONNABORTED:
  266. rxperf_log_error(call, call->abort_code);
  267. goto call_complete;
  268. case -EOPNOTSUPP:
  269. abort_code = RXGEN_OPCODE;
  270. rxrpc_kernel_abort_call(rxperf_socket, call->rxcall,
  271. abort_code, ret,
  272. rxperf_abort_op_not_supported);
  273. goto call_complete;
  274. case -ENOTSUPP:
  275. abort_code = RX_USER_ABORT;
  276. rxrpc_kernel_abort_call(rxperf_socket, call->rxcall,
  277. abort_code, ret,
  278. rxperf_abort_op_not_supported);
  279. goto call_complete;
  280. case -EIO:
  281. pr_err("Call %u in bad state %u\n",
  282. call->debug_id, call->state);
  283. fallthrough;
  284. case -ENODATA:
  285. case -EBADMSG:
  286. case -EMSGSIZE:
  287. case -ENOMEM:
  288. case -EFAULT:
  289. rxrpc_kernel_abort_call(rxperf_socket, call->rxcall,
  290. RXGEN_SS_UNMARSHAL, ret,
  291. rxperf_abort_unmarshal_error);
  292. goto call_complete;
  293. default:
  294. rxrpc_kernel_abort_call(rxperf_socket, call->rxcall,
  295. RX_CALL_DEAD, ret,
  296. rxperf_abort_general_error);
  297. goto call_complete;
  298. }
  299. }
  300. call_complete:
  301. rxperf_set_call_complete(call, ret, remote_abort);
  302. /* The call may have been requeued */
  303. rxrpc_kernel_shutdown_call(rxperf_socket, call->rxcall);
  304. rxrpc_kernel_put_call(rxperf_socket, call->rxcall);
  305. cancel_work(&call->work);
  306. kfree(call);
  307. }
  308. /*
  309. * Extract a piece of data from the received data socket buffers.
  310. */
  311. static int rxperf_extract_data(struct rxperf_call *call, bool want_more)
  312. {
  313. u32 remote_abort = 0;
  314. int ret;
  315. ret = rxrpc_kernel_recv_data(rxperf_socket, call->rxcall, &call->iter,
  316. &call->iov_len, want_more, &remote_abort,
  317. &call->service_id);
  318. pr_debug("Extract i=%zu l=%zu m=%u ret=%d\n",
  319. iov_iter_count(&call->iter), call->iov_len, want_more, ret);
  320. if (ret == 0 || ret == -EAGAIN)
  321. return ret;
  322. if (ret == 1) {
  323. switch (call->state) {
  324. case RXPERF_CALL_SV_AWAIT_REQUEST:
  325. rxperf_set_call_state(call, RXPERF_CALL_SV_REPLYING);
  326. break;
  327. case RXPERF_CALL_COMPLETE:
  328. pr_debug("premature completion %d", call->error);
  329. return call->error;
  330. default:
  331. break;
  332. }
  333. return 0;
  334. }
  335. rxperf_set_call_complete(call, ret, remote_abort);
  336. return ret;
  337. }
  338. /*
  339. * Grab the operation ID from an incoming manager call.
  340. */
  341. static int rxperf_deliver_param_block(struct rxperf_call *call)
  342. {
  343. u32 version;
  344. int ret;
  345. /* Extract the parameter block */
  346. ret = rxperf_extract_data(call, true);
  347. if (ret < 0)
  348. return ret;
  349. version = ntohl(call->params.version);
  350. call->operation_id = ntohl(call->params.type);
  351. call->deliver = rxperf_deliver_request;
  352. if (version != RX_PERF_VERSION) {
  353. pr_info("Version mismatch %x\n", version);
  354. return -ENOTSUPP;
  355. }
  356. switch (call->operation_id) {
  357. case RX_PERF_SEND:
  358. call->type = "send";
  359. call->reply_len = 0;
  360. call->iov_len = 4; /* Expect req size */
  361. break;
  362. case RX_PERF_RECV:
  363. call->type = "recv";
  364. call->req_len = 0;
  365. call->iov_len = 4; /* Expect reply size */
  366. break;
  367. case RX_PERF_RPC:
  368. call->type = "rpc";
  369. call->iov_len = 8; /* Expect req size and reply size */
  370. break;
  371. case RX_PERF_FILE:
  372. call->type = "file";
  373. fallthrough;
  374. default:
  375. return -EOPNOTSUPP;
  376. }
  377. rxperf_set_call_state(call, RXPERF_CALL_SV_AWAIT_REQUEST);
  378. return call->deliver(call);
  379. }
  380. /*
  381. * Deliver the request data.
  382. */
  383. static int rxperf_deliver_request(struct rxperf_call *call)
  384. {
  385. int ret;
  386. switch (call->unmarshal) {
  387. case 0:
  388. call->kvec[0].iov_len = call->iov_len;
  389. call->kvec[0].iov_base = call->tmp;
  390. iov_iter_kvec(&call->iter, READ, call->kvec, 1, call->iov_len);
  391. call->unmarshal++;
  392. fallthrough;
  393. case 1:
  394. ret = rxperf_extract_data(call, true);
  395. if (ret < 0)
  396. return ret;
  397. switch (call->operation_id) {
  398. case RX_PERF_SEND:
  399. call->type = "send";
  400. call->req_len = ntohl(call->tmp[0]);
  401. call->reply_len = 0;
  402. break;
  403. case RX_PERF_RECV:
  404. call->type = "recv";
  405. call->req_len = 0;
  406. call->reply_len = ntohl(call->tmp[0]);
  407. break;
  408. case RX_PERF_RPC:
  409. call->type = "rpc";
  410. call->req_len = ntohl(call->tmp[0]);
  411. call->reply_len = ntohl(call->tmp[1]);
  412. break;
  413. default:
  414. pr_info("Can't parse extra params\n");
  415. return -EIO;
  416. }
  417. pr_debug("CALL op=%s rq=%zx rp=%zx\n",
  418. call->type, call->req_len, call->reply_len);
  419. call->iov_len = call->req_len;
  420. iov_iter_discard(&call->iter, READ, call->req_len);
  421. call->unmarshal++;
  422. fallthrough;
  423. case 2:
  424. ret = rxperf_extract_data(call, true);
  425. if (ret < 0)
  426. return ret;
  427. /* Deal with the terminal magic cookie. */
  428. call->iov_len = 4;
  429. call->kvec[0].iov_len = call->iov_len;
  430. call->kvec[0].iov_base = call->tmp;
  431. iov_iter_kvec(&call->iter, READ, call->kvec, 1, call->iov_len);
  432. call->unmarshal++;
  433. fallthrough;
  434. case 3:
  435. ret = rxperf_extract_data(call, false);
  436. if (ret < 0)
  437. return ret;
  438. call->unmarshal++;
  439. fallthrough;
  440. default:
  441. return 0;
  442. }
  443. }
  444. /*
  445. * Process a call for which we've received the request.
  446. */
  447. static int rxperf_process_call(struct rxperf_call *call)
  448. {
  449. struct msghdr msg = {};
  450. struct bio_vec bv;
  451. struct kvec iov[1];
  452. ssize_t n;
  453. size_t reply_len = call->reply_len, len;
  454. rxrpc_kernel_set_tx_length(rxperf_socket, call->rxcall,
  455. reply_len + sizeof(rxperf_magic_cookie));
  456. while (reply_len > 0) {
  457. len = umin(reply_len, PAGE_SIZE);
  458. bvec_set_page(&bv, ZERO_PAGE(0), len, 0);
  459. iov_iter_bvec(&msg.msg_iter, WRITE, &bv, 1, len);
  460. msg.msg_flags = MSG_MORE;
  461. n = rxrpc_kernel_send_data(rxperf_socket, call->rxcall, &msg,
  462. len, rxperf_notify_end_reply_tx);
  463. if (n < 0)
  464. return n;
  465. if (n == 0)
  466. return -EIO;
  467. reply_len -= n;
  468. }
  469. len = sizeof(rxperf_magic_cookie);
  470. iov[0].iov_base = (void *)rxperf_magic_cookie;
  471. iov[0].iov_len = len;
  472. iov_iter_kvec(&msg.msg_iter, WRITE, iov, 1, len);
  473. msg.msg_flags = 0;
  474. n = rxrpc_kernel_send_data(rxperf_socket, call->rxcall, &msg, len,
  475. rxperf_notify_end_reply_tx);
  476. if (n >= 0)
  477. return 0; /* Success */
  478. if (n == -ENOMEM)
  479. rxrpc_kernel_abort_call(rxperf_socket, call->rxcall,
  480. RXGEN_SS_MARSHAL, -ENOMEM,
  481. rxperf_abort_oom);
  482. return n;
  483. }
  484. /*
  485. * Add an rxkad key to the security keyring.
  486. */
  487. static int rxperf_add_rxkad_key(struct key *keyring)
  488. {
  489. key_ref_t kref;
  490. int ret;
  491. kref = key_create_or_update(make_key_ref(keyring, true),
  492. "rxrpc_s",
  493. __stringify(RX_PERF_SERVICE) ":2",
  494. secret,
  495. sizeof(secret),
  496. KEY_POS_VIEW | KEY_POS_READ | KEY_POS_SEARCH
  497. | KEY_USR_VIEW,
  498. KEY_ALLOC_NOT_IN_QUOTA);
  499. if (IS_ERR(kref)) {
  500. pr_err("Can't allocate rxperf server key: %ld\n", PTR_ERR(kref));
  501. return PTR_ERR(kref);
  502. }
  503. ret = key_link(keyring, key_ref_to_ptr(kref));
  504. if (ret < 0)
  505. pr_err("Can't link rxperf server key: %d\n", ret);
  506. key_ref_put(kref);
  507. return ret;
  508. }
  509. #ifdef CONFIG_RXGK
  510. /*
  511. * Add a yfs-rxgk key to the security keyring.
  512. */
  513. static int rxperf_add_yfs_rxgk_key(struct key *keyring, u32 enctype)
  514. {
  515. const struct krb5_enctype *krb5 = crypto_krb5_find_enctype(enctype);
  516. key_ref_t kref;
  517. char name[64];
  518. int ret;
  519. u8 key[32];
  520. if (!krb5 || krb5->key_len > sizeof(key))
  521. return 0;
  522. /* The key is just { 0, 1, 2, 3, 4, ... } */
  523. for (int i = 0; i < krb5->key_len; i++)
  524. key[i] = i;
  525. sprintf(name, "%u:6:1:%u", RX_PERF_SERVICE, enctype);
  526. kref = key_create_or_update(make_key_ref(keyring, true),
  527. "rxrpc_s", name,
  528. key, krb5->key_len,
  529. KEY_POS_VIEW | KEY_POS_READ | KEY_POS_SEARCH |
  530. KEY_USR_VIEW,
  531. KEY_ALLOC_NOT_IN_QUOTA);
  532. if (IS_ERR(kref)) {
  533. pr_err("Can't allocate rxperf server key: %ld\n", PTR_ERR(kref));
  534. return PTR_ERR(kref);
  535. }
  536. ret = key_link(keyring, key_ref_to_ptr(kref));
  537. if (ret < 0)
  538. pr_err("Can't link rxperf server key: %d\n", ret);
  539. key_ref_put(kref);
  540. return ret;
  541. }
  542. #endif
  543. /*
  544. * Initialise the rxperf server.
  545. */
  546. static int __init rxperf_init(void)
  547. {
  548. struct key *keyring;
  549. int ret = -ENOMEM;
  550. pr_info("Server registering\n");
  551. rxperf_workqueue = alloc_workqueue("rxperf", WQ_PERCPU, 0);
  552. if (!rxperf_workqueue)
  553. goto error_workqueue;
  554. keyring = keyring_alloc("rxperf_server",
  555. GLOBAL_ROOT_UID, GLOBAL_ROOT_GID, current_cred(),
  556. KEY_POS_VIEW | KEY_POS_READ | KEY_POS_SEARCH |
  557. KEY_POS_WRITE |
  558. KEY_USR_VIEW | KEY_USR_READ | KEY_USR_SEARCH |
  559. KEY_USR_WRITE |
  560. KEY_OTH_VIEW | KEY_OTH_READ | KEY_OTH_SEARCH,
  561. KEY_ALLOC_NOT_IN_QUOTA,
  562. NULL, NULL);
  563. if (IS_ERR(keyring)) {
  564. pr_err("Can't allocate rxperf server keyring: %ld\n",
  565. PTR_ERR(keyring));
  566. goto error_keyring;
  567. }
  568. rxperf_sec_keyring = keyring;
  569. ret = rxperf_add_rxkad_key(keyring);
  570. if (ret < 0)
  571. goto error_key;
  572. #ifdef CONFIG_RXGK
  573. ret = rxperf_add_yfs_rxgk_key(keyring, KRB5_ENCTYPE_AES128_CTS_HMAC_SHA1_96);
  574. if (ret < 0)
  575. goto error_key;
  576. ret = rxperf_add_yfs_rxgk_key(keyring, KRB5_ENCTYPE_AES256_CTS_HMAC_SHA1_96);
  577. if (ret < 0)
  578. goto error_key;
  579. ret = rxperf_add_yfs_rxgk_key(keyring, KRB5_ENCTYPE_AES128_CTS_HMAC_SHA256_128);
  580. if (ret < 0)
  581. goto error_key;
  582. ret = rxperf_add_yfs_rxgk_key(keyring, KRB5_ENCTYPE_AES256_CTS_HMAC_SHA384_192);
  583. if (ret < 0)
  584. goto error_key;
  585. ret = rxperf_add_yfs_rxgk_key(keyring, KRB5_ENCTYPE_CAMELLIA128_CTS_CMAC);
  586. if (ret < 0)
  587. goto error_key;
  588. ret = rxperf_add_yfs_rxgk_key(keyring, KRB5_ENCTYPE_CAMELLIA256_CTS_CMAC);
  589. if (ret < 0)
  590. goto error_key;
  591. #endif
  592. ret = rxperf_open_socket();
  593. if (ret < 0)
  594. goto error_socket;
  595. return 0;
  596. error_socket:
  597. error_key:
  598. key_put(rxperf_sec_keyring);
  599. error_keyring:
  600. destroy_workqueue(rxperf_workqueue);
  601. rcu_barrier();
  602. error_workqueue:
  603. pr_err("Failed to register: %d\n", ret);
  604. return ret;
  605. }
  606. late_initcall(rxperf_init); /* Must be called after net/ to create socket */
  607. static void __exit rxperf_exit(void)
  608. {
  609. pr_info("Server unregistering.\n");
  610. rxperf_close_socket();
  611. key_put(rxperf_sec_keyring);
  612. destroy_workqueue(rxperf_workqueue);
  613. rcu_barrier();
  614. }
  615. module_exit(rxperf_exit);