diff options
author | Jerry Jelinek <jerry.jelinek@joyent.com> | 2018-08-30 12:06:40 +0000 |
---|---|---|
committer | Jerry Jelinek <jerry.jelinek@joyent.com> | 2018-08-30 12:06:40 +0000 |
commit | 6e567b7bf9c30262784d63ef8e2ad150be55b6c1 (patch) | |
tree | c666cdbd007803e131f981c932340e944b3c71f1 | |
parent | fb2422a25cfeb7137e66e7a24541eafb83165362 (diff) | |
parent | 44a84c183ccfba4ca8eb08835c722bd833daf781 (diff) | |
download | illumos-joyent-6e567b7bf9c30262784d63ef8e2ad150be55b6c1.tar.gz |
[illumos-gate merge]
commit 44a84c183ccfba4ca8eb08835c722bd833daf781
9772 Panic in ahci when the failed slot spkt is NULL
commit 4a3b05278938491ea95d557939c130d3eb17cfd4
3354 kernel crash in rpcsec_gss after using gsscred
-rw-r--r-- | usr/src/uts/common/io/sata/adapters/ahci/ahci.c | 84 | ||||
-rw-r--r-- | usr/src/uts/common/rpc/rpcmod.c | 48 | ||||
-rw-r--r-- | usr/src/uts/common/rpc/sec_gss/svc_rpcsec_gss.c | 183 | ||||
-rw-r--r-- | usr/src/uts/common/rpc/svc.c | 33 | ||||
-rw-r--r-- | usr/src/uts/common/rpc/svc.h | 41 | ||||
-rw-r--r-- | usr/src/uts/common/rpc/svc_clts.c | 10 | ||||
-rw-r--r-- | usr/src/uts/common/rpc/svc_cots.c | 10 | ||||
-rw-r--r-- | usr/src/uts/common/rpc/svc_rdma.c | 8 |
8 files changed, 216 insertions, 201 deletions
diff --git a/usr/src/uts/common/io/sata/adapters/ahci/ahci.c b/usr/src/uts/common/io/sata/adapters/ahci/ahci.c index 07466f8c77..8a7b1be281 100644 --- a/usr/src/uts/common/io/sata/adapters/ahci/ahci.c +++ b/usr/src/uts/common/io/sata/adapters/ahci/ahci.c @@ -23,6 +23,7 @@ * Copyright (c) 2006, 2010, Oracle and/or its affiliates. All rights reserved. * Copyright 2018 Nexenta Systems, Inc. All rights reserved. * Copyright (c) 2018, Joyent, Inc. + * Copyright 2018 OmniOS Community Edition (OmniOSce) Association. */ /* @@ -1274,7 +1275,7 @@ ahci_getinfo(dev_info_t *dip, ddi_info_cmd_t infocmd, static int ahci_register_sata_hba_tran(ahci_ctl_t *ahci_ctlp, uint32_t cap_status) { - struct sata_hba_tran *sata_hba_tran; + struct sata_hba_tran *sata_hba_tran; AHCIDBG(AHCIDBG_INIT|AHCIDBG_ENTRY, ahci_ctlp, "ahci_register_sata_hba_tran enter", NULL); @@ -1976,8 +1977,8 @@ ahci_do_sync_start(ahci_ctl_t *ahci_ctlp, ahci_port_t *ahci_portp, * * NOTE: it will always return slot 0 for following commands to simplify the * algorithm. - * 1. REQUEST SENSE or READ LOG EXT command during error recovery process - * 2. READ/WRITE PORTMULT command + * 1. REQUEST SENSE or READ LOG EXT command during error recovery process + * 2. READ/WRITE PORTMULT command */ static int ahci_claim_free_slot(ahci_ctl_t *ahci_ctlp, ahci_port_t *ahci_portp, @@ -2133,7 +2134,7 @@ out: * Builds the Command Table for the sata packet and delivers it to controller. * * Returns: - * slot number if we can obtain a slot successfully + * slot number if we can obtain a slot successfully * otherwise, return AHCI_FAILURE */ static int @@ -2252,17 +2253,17 @@ ahci_deliver_satapkt(ahci_ctl_t *ahci_ctlp, ahci_port_t *ahci_portp, case 0: /* * satacmd_addr_type will be 0 for the commands below: - * ATAPI command - * SATAC_IDLE_IM - * SATAC_STANDBY_IM - * SATAC_DOWNLOAD_MICROCODE - * SATAC_FLUSH_CACHE - * SATAC_SET_FEATURES - * SATAC_SMART - * SATAC_ID_PACKET_DEVICE - * SATAC_ID_DEVICE - * SATAC_READ_PORTMULT - * SATAC_WRITE_PORTMULT + * ATAPI command + * SATAC_IDLE_IM + * SATAC_STANDBY_IM + * SATAC_DOWNLOAD_MICROCODE + * SATAC_FLUSH_CACHE + * SATAC_SET_FEATURES + * SATAC_SMART + * SATAC_ID_PACKET_DEVICE + * SATAC_ID_DEVICE + * SATAC_READ_PORTMULT + * SATAC_WRITE_PORTMULT */ /* FALLTHRU */ @@ -6830,10 +6831,10 @@ ahci_intr(caddr_t arg1, caddr_t arg2) * AHCI_INTR_STATUS_DHRS means a D2H Register FIS has been received * with the 'I' bit set. And the following commands will send thus * FIS with 'I' bit set upon the successful completion: - * 1. Non-data commands - * 2. DMA data-in command - * 3. DMA data-out command - * 4. PIO data-out command + * 1. Non-data commands + * 2. DMA data-in command + * 3. DMA data-out command + * 4. PIO data-out command * 5. PACKET non-data commands * 6. PACKET PIO data-in command * 7. PACKET PIO data-out command @@ -6843,7 +6844,7 @@ ahci_intr(caddr_t arg1, caddr_t arg2) * AHCI_INTR_STATUS_PSS means a PIO Setup FIS has been received * with the 'I' bit set. And the following commands will send this * FIS upon the successful completion: - * 1. PIO data-in command + * 1. PIO data-in command */ static int ahci_intr_cmd_cmplt(ahci_ctl_t *ahci_ctlp, @@ -7797,7 +7798,7 @@ out: * HBA, and the respective PxSERR register bit will be set. And PxIS.IFS * (fatal) or PxIS.INFS (non-fatal) will be set. The conditions that * causes PxIS.IFS/PxIS.INFS to be set are - * 1. in PxSERR.ERR, P bit is set to '1' + * 1. in PxSERR.ERR, P bit is set to '1' * 2. in PxSERR.DIAG, C or H bit is set to '1' * 3. PhyRdy drop unexpectly, N bit is set to '1' * If the error occurred during a non-data FIS, the FIS must be @@ -8498,7 +8499,7 @@ ahci_put_port_into_notrunning_state(ahci_ctl_t *ahci_ctlp, * the process. * * The routine will be called under following scenarios: - * + To reset the HBA + * + To reset the HBA * + To abort the packet(s) * + To reset the port * + To activate the port @@ -9570,8 +9571,8 @@ out: /* * Used to recovery a PMULT pmport fatal error under FIS-based switching. - * 1. device specific.PxFBS.SDE=1 - * 2. Non-Deivce specific. + * 1. device specific.PxFBS.SDE=1 + * 2. Non Device specific. * Nothing will be done when Command-based switching is employed. * * Currently code is neither completed nor tested. @@ -10085,23 +10086,24 @@ ahci_dump_commands(ahci_ctl_t *ahci_ctlp, uint8_t port, } spkt = ahci_portp->ahciport_slot_pkts[tmp_slot]; - ASSERT(spkt != NULL); - cmd = spkt->satapkt_cmd; - - cmn_err(CE_WARN, "!satapkt 0x%p: cmd_reg = 0x%x " - "features_reg = 0x%x sec_count_msb = 0x%x " - "lba_low_msb = 0x%x lba_mid_msb = 0x%x " - "lba_high_msb = 0x%x sec_count_lsb = 0x%x " - "lba_low_lsb = 0x%x lba_mid_lsb = 0x%x " - "lba_high_lsb = 0x%x device_reg = 0x%x " - "addr_type = 0x%x cmd_flags = 0x%x", (void *)spkt, - cmd.satacmd_cmd_reg, cmd.satacmd_features_reg, - cmd.satacmd_sec_count_msb, cmd.satacmd_lba_low_msb, - cmd.satacmd_lba_mid_msb, cmd.satacmd_lba_high_msb, - cmd.satacmd_sec_count_lsb, cmd.satacmd_lba_low_lsb, - cmd.satacmd_lba_mid_lsb, cmd.satacmd_lba_high_lsb, - cmd.satacmd_device_reg, cmd.satacmd_addr_type, - *((uint32_t *)&(cmd.satacmd_flags))); + if (spkt != NULL) { + cmd = spkt->satapkt_cmd; + + cmn_err(CE_WARN, "!satapkt 0x%p: cmd_reg = 0x%x " + "features_reg = 0x%x sec_count_msb = 0x%x " + "lba_low_msb = 0x%x lba_mid_msb = 0x%x " + "lba_high_msb = 0x%x sec_count_lsb = 0x%x " + "lba_low_lsb = 0x%x lba_mid_lsb = 0x%x " + "lba_high_lsb = 0x%x device_reg = 0x%x " + "addr_type = 0x%x cmd_flags = 0x%x", (void *)spkt, + cmd.satacmd_cmd_reg, cmd.satacmd_features_reg, + cmd.satacmd_sec_count_msb, cmd.satacmd_lba_low_msb, + cmd.satacmd_lba_mid_msb, cmd.satacmd_lba_high_msb, + cmd.satacmd_sec_count_lsb, cmd.satacmd_lba_low_lsb, + cmd.satacmd_lba_mid_lsb, cmd.satacmd_lba_high_lsb, + cmd.satacmd_device_reg, cmd.satacmd_addr_type, + *((uint32_t *)&(cmd.satacmd_flags))); + } CLEAR_BIT(slot_tags, tmp_slot); } diff --git a/usr/src/uts/common/rpc/rpcmod.c b/usr/src/uts/common/rpc/rpcmod.c index c8e7220bc7..a59f6e785b 100644 --- a/usr/src/uts/common/rpc/rpcmod.c +++ b/usr/src/uts/common/rpc/rpcmod.c @@ -24,12 +24,14 @@ */ /* * Copyright 2012 Milan Jurik. All rights reserved. + * Copyright 2012 Marcel Telka <marcel@telka.sk> * Copyright 2013 Nexenta Systems, Inc. All rights reserved. + * Copyright 2018 OmniOS Community Edition (OmniOSce) Association. */ /* Copyright (c) 1990 Mentat Inc. */ /* Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T */ -/* All Rights Reserved */ +/* All Rights Reserved */ /* * Kernel RPC filtering module @@ -570,7 +572,6 @@ rmm_close(queue_t *q, int flag, cred_t *crp) return ((*((struct temp_slot *)q->q_ptr)->ops->xo_close)(q, flag, crp)); } -static void rpcmod_release(queue_t *, mblk_t *, bool_t); /* * rpcmodopen - open routine gets called when the module gets pushed * onto the stream. @@ -581,19 +582,9 @@ rpcmodopen(queue_t *q, dev_t *devp, int flag, int sflag, cred_t *crp) { struct rpcm *rmp; - extern void (*rpc_rele)(queue_t *, mblk_t *, bool_t); - TRACE_0(TR_FAC_KRPC, TR_RPCMODOPEN_START, "rpcmodopen_start:"); /* - * Initialize entry points to release a rpcmod slot (and an input - * message if supplied) and to send an output message to the module - * below rpcmod. - */ - if (rpc_rele == NULL) - rpc_rele = rpcmod_release; - - /* * Only sufficiently privileged users can use this module, and it * is assumed that they will use this module properly, and NOT send * bulk data from downstream. @@ -950,9 +941,20 @@ rpcmodwsrv(queue_t *q) } } -/* ARGSUSED */ -static void -rpcmod_release(queue_t *q, mblk_t *bp, bool_t enable) +void +rpcmod_hold(queue_t *q) +{ + struct rpcm *rmp = (struct rpcm *)q->q_ptr; + + mutex_enter(&rmp->rm_lock); + rmp->rm_ref++; + mutex_exit(&rmp->rm_lock); +} + +void +rpcmod_release(queue_t *q, mblk_t *bp, + /* LINTED E_FUNC_ARG_UNUSED */ + bool_t enable __unused) { struct rpcm *rmp; @@ -1005,7 +1007,6 @@ rpcmod_release(queue_t *q, mblk_t *bp, bool_t enable) static int mir_clnt_dup_request(queue_t *q, mblk_t *mp); static void mir_rput_proto(queue_t *q, mblk_t *mp); static int mir_svc_policy_notify(queue_t *q, int event); -static void mir_svc_release(queue_t *wq, mblk_t *mp, bool_t); static void mir_svc_start(queue_t *wq); static void mir_svc_idle_start(queue_t *, mir_t *); static void mir_svc_idle_stop(queue_t *, mir_t *); @@ -1020,7 +1021,6 @@ static void mir_disconnect(queue_t *, mir_t *ir); static int mir_check_len(queue_t *, mblk_t *); static void mir_timer(void *); -extern void (*mir_rele)(queue_t *, mblk_t *, bool_t); extern void (*mir_start)(queue_t *); extern void (*clnt_stop_idle)(queue_t *); @@ -1259,8 +1259,6 @@ mir_open(queue_t *q, dev_t *devp, int flag, int sflag, cred_t *credp) RPCLOG(32, "rpcmod: mir_open of q 0x%p\n", (void *)q); /* Set variables used directly by kRPC. */ - if (!mir_rele) - mir_rele = mir_svc_release; if (!mir_start) mir_start = mir_svc_start; if (!clnt_stop_idle) @@ -2019,11 +2017,21 @@ mir_svc_start_close(queue_t *wq, mir_t *mir) qenable(wq); } +void +mir_svc_hold(queue_t *wq) +{ + mir_t *mir = (mir_t *)wq->q_ptr; + + mutex_enter(&mir->mir_mutex); + mir->mir_ref_cnt++; + mutex_exit(&mir->mir_mutex); +} + /* * This routine is called directly by kRPC after a request is completed, * whether a reply was sent or the request was dropped. */ -static void +void mir_svc_release(queue_t *wq, mblk_t *mp, bool_t enable) { mir_t *mir = (mir_t *)wq->q_ptr; diff --git a/usr/src/uts/common/rpc/sec_gss/svc_rpcsec_gss.c b/usr/src/uts/common/rpc/sec_gss/svc_rpcsec_gss.c index 23f98b982c..aa0eb2484e 100644 --- a/usr/src/uts/common/rpc/sec_gss/svc_rpcsec_gss.c +++ b/usr/src/uts/common/rpc/sec_gss/svc_rpcsec_gss.c @@ -23,6 +23,8 @@ * Copyright 2015 Nexenta Systems, Inc. All rights reserved. * Copyright (c) 1996, 2010, Oracle and/or its affiliates. All rights reserved. * Copyright 2012 Milan Jurik. All rights reserved. + * Copyright 2012 Marcel Telka <marcel@telka.sk> + * Copyright 2018 OmniOS Community Edition (OmniOSce) Association. */ /* @@ -374,10 +376,7 @@ rpc_gss_cleanup(SVCXPRT *clone_xprt) * Shift the array arr of length arrlen right by nbits bits. */ static void -shift_bits(arr, arrlen, nbits) - uint_t *arr; - int arrlen; - int nbits; +shift_bits(uint_t *arr, int arrlen, int nbits) { int i, j; uint_t lo, hi; @@ -407,10 +406,7 @@ shift_bits(arr, arrlen, nbits) * Check that the received sequence number seq_num is valid. */ static bool_t -check_seq(cl, seq_num, kill_context) - svc_rpc_gss_data *cl; - uint_t seq_num; - bool_t *kill_context; +check_seq(svc_rpc_gss_data *cl, uint_t seq_num, bool_t *kill_context) { int i, j; uint_t bit; @@ -431,7 +427,7 @@ check_seq(cl, seq_num, kill_context) */ if (seq_num > cl->seq_num) { (void) shift_bits(cl->seq_bits, SEQ_ARR_SIZE, - (int)(seq_num - cl->seq_num)); + (int)(seq_num - cl->seq_num)); cl->seq_bits[0] |= SEQ_HI_BIT; cl->seq_num = seq_num; return (TRUE); @@ -465,8 +461,7 @@ check_seq(cl, seq_num, kill_context) * Set server callback. */ bool_t -rpc_gss_set_callback(cb) - rpc_gss_callback_t *cb; +rpc_gss_set_callback(rpc_gss_callback_t *cb) { rpc_gss_cblist_t *cbl, *tmp; @@ -508,9 +503,7 @@ rpc_gss_set_callback(cb) * the incoming context. */ static bool_t -do_callback(req, client_data) - struct svc_req *req; - svc_rpc_gss_data *client_data; +do_callback(struct svc_req *req, svc_rpc_gss_data *client_data) { rpc_gss_cblist_t *cbl; bool_t ret = TRUE, found = FALSE; @@ -519,13 +512,13 @@ do_callback(req, client_data) mutex_enter(&cb_mutex); for (cbl = rpc_gss_cblist; cbl != NULL; cbl = cbl->next) { if (req->rq_prog != cbl->cb.program || - req->rq_vers != cbl->cb.version) + req->rq_vers != cbl->cb.version) continue; found = TRUE; lock.locked = FALSE; lock.raw_cred = &client_data->raw_cred; ret = (*cbl->cb.callback)(req, client_data->deleg, - client_data->context, &lock, &client_data->cookie); + client_data->context, &lock, &client_data->cookie); req->rq_xprt->xp_cookie = client_data->cookie; if (ret) { @@ -537,7 +530,7 @@ do_callback(req, client_data) if (!found) { if (client_data->deleg != GSS_C_NO_CREDENTIAL) { (void) kgss_release_cred(&minor, &client_data->deleg, - crgetuid(CRED())); + crgetuid(CRED())); client_data->deleg = GSS_C_NO_CREDENTIAL; } } @@ -549,11 +542,8 @@ do_callback(req, client_data) * Get caller credentials. */ bool_t -rpc_gss_getcred(req, rcred, ucred, cookie) - struct svc_req *req; - rpc_gss_rawcred_t **rcred; - rpc_gss_ucred_t **ucred; - void **cookie; +rpc_gss_getcred(struct svc_req *req, rpc_gss_rawcred_t **rcred, + rpc_gss_ucred_t **ucred, void **cookie) { SVCAUTH *svcauth; svc_rpc_gss_data *client_data; @@ -573,38 +563,45 @@ rpc_gss_getcred(req, rcred, ucred, cookie) if (client_data->u_cred_set == 0 || client_data->u_cred_set < gethrestime_sec()) { - if (client_data->u_cred_set == 0) { - if ((gssstat = kgsscred_expname_to_unix_cred( - &client_data->client_name, - &client_data->u_cred.uid, - &client_data->u_cred.gid, - &client_data->u_cred.gidlist, - &gidlen, crgetuid(CRED()))) != GSS_S_COMPLETE) { - RPCGSS_LOG(1, "rpc_gss_getcred: " - "kgsscred_expname_to_unix_cred failed %x\n", - gssstat); - *ucred = NULL; - } else { - client_data->u_cred.gidlen = (short)gidlen; - client_data->u_cred_set = - gethrestime_sec() + svc_rpcgss_gid_timeout; + if (client_data->u_cred_set == 0) { + if ((gssstat = kgsscred_expname_to_unix_cred( + &client_data->client_name, + &client_data->u_cred.uid, + &client_data->u_cred.gid, + &client_data->u_cred.gidlist, + &gidlen, crgetuid(CRED()))) + != GSS_S_COMPLETE) { + RPCGSS_LOG(1, "rpc_gss_getcred: " + "kgsscred_expname_to_unix_cred " + "failed %x\n", gssstat); + *ucred = NULL; + } else { + client_data->u_cred.gidlen = + (short)gidlen; + client_data->u_cred_set = + gethrestime_sec() + + svc_rpcgss_gid_timeout; + } + } else if (client_data->u_cred_set + < gethrestime_sec()) { + if ((gssstat = kgss_get_group_info( + client_data->u_cred.uid, + &client_data->u_cred.gid, + &client_data->u_cred.gidlist, + &gidlen, crgetuid(CRED()))) + != GSS_S_COMPLETE) { + RPCGSS_LOG(1, "rpc_gss_getcred: " + "kgss_get_group_info failed %x\n", + gssstat); + *ucred = NULL; + } else { + client_data->u_cred.gidlen = + (short)gidlen; + client_data->u_cred_set = + gethrestime_sec() + + svc_rpcgss_gid_timeout; + } } - } else if (client_data->u_cred_set < gethrestime_sec()) { - if ((gssstat = kgss_get_group_info( - client_data->u_cred.uid, - &client_data->u_cred.gid, - &client_data->u_cred.gidlist, - &gidlen, crgetuid(CRED()))) != GSS_S_COMPLETE) { - RPCGSS_LOG(1, "rpc_gss_getcred: " - "kgss_get_group_info failed %x\n", - gssstat); - *ucred = NULL; - } else { - client_data->u_cred.gidlen = (short)gidlen; - client_data->u_cred_set = - gethrestime_sec() + svc_rpcgss_gid_timeout; - } - } } } @@ -694,7 +691,7 @@ do_gss_accept( gss_buffer_desc output_token; OM_uint32 gssstat, minor, minor_stat, time_rec; int ret_flags, ret; - gss_OID mech_type = GSS_C_NULL_OID; + gss_OID mech_type = GSS_C_NULL_OID; int free_mech_type = 1; struct svc_req r, *rqst; @@ -909,6 +906,7 @@ svcrpcsec_gss_taskq_func(void *svcrpcsecgss_taskq_arg) retval); } rpc_msg_free(&arg->msg, MAX_AUTH_BYTES); + SVC_RELE(arg->rq_xprt, NULL, FALSE); svc_clone_unlink(arg->rq_xprt); svc_clone_free(arg->rq_xprt); xdr_free(__xdr_rpc_gss_init_arg, (caddr_t)arg->rpc_call_arg); @@ -974,6 +972,11 @@ rpcsec_gss_init( svc_clone_link(rqst->rq_xprt->xp_master, arg->rq_xprt, rqst->rq_xprt); arg->rq_xprt->xp_xid = rqst->rq_xprt->xp_xid; + /* + * Increment the reference count on the rpcmod slot so that is not + * freed before the task has finished. + */ + SVC_HOLD(arg->rq_xprt); /* set the appropriate wrap/unwrap routine for RPCSEC_GSS */ arg->rq_xprt->xp_auth.svc_ah_ops = svc_rpc_gss_ops; @@ -993,6 +996,7 @@ rpcsec_gss_init( cmn_err(CE_NOTE, "rpcsec_gss_init: taskq dispatch fail"); ret = RPCSEC_GSS_FAILED; rpc_msg_free(&arg->msg, MAX_AUTH_BYTES); + SVC_RELE(arg->rq_xprt, NULL, FALSE); svc_clone_unlink(arg->rq_xprt); svc_clone_free(arg->rq_xprt); kmem_free(arg, sizeof (*arg)); @@ -1473,11 +1477,8 @@ check_verf(struct rpc_msg *msg, gss_ctx_id_t context, int *qop_state, uid_t uid) * (e.g. sequence number or sequence window) */ static bool_t -set_response_verf(rqst, msg, cl, num) - struct svc_req *rqst; - struct rpc_msg *msg; - svc_rpc_gss_data *cl; - uint_t num; +set_response_verf(struct svc_req *rqst, struct rpc_msg *msg, + svc_rpc_gss_data *cl, uint_t num) { OM_uint32 minor; gss_buffer_desc in_buf, out_buf; @@ -1488,8 +1489,8 @@ set_response_verf(rqst, msg, cl, num) in_buf.value = (char *)&num_net; /* XXX uid ? */ - if ((kgss_sign(&minor, cl->context, cl->qop, &in_buf, - &out_buf)) != GSS_S_COMPLETE) + if ((kgss_sign(&minor, cl->context, cl->qop, &in_buf, &out_buf)) + != GSS_S_COMPLETE) return (FALSE); rqst->rq_xprt->xp_verf.oa_flavor = RPCSEC_GSS; @@ -1564,8 +1565,7 @@ create_client() * Insert client context into hash list and LRU list. */ static void -insert_client(client_data) - svc_rpc_gss_data *client_data; +insert_client(svc_rpc_gss_data *client_data) { svc_rpc_gss_data *cl; int index = HASH(client_data->key); @@ -1593,8 +1593,7 @@ insert_client(client_data) * top of the LRU list since this is the most recently used context. */ static svc_rpc_gss_data * -get_client(ctx_handle) - gss_buffer_t ctx_handle; +get_client(gss_buffer_t ctx_handle) { uint_t key = *(uint_t *)ctx_handle->value; svc_rpc_gss_data *cl; @@ -1636,8 +1635,7 @@ get_client(ctx_handle) * Don't change its LRU state since it may not be used. */ static svc_rpc_gss_data * -find_client(key) - uint_t key; +find_client(uint_t key) { int index = HASH(key); svc_rpc_gss_data *cl = NULL; @@ -1655,8 +1653,7 @@ find_client(key) * Destroy a client context. */ static void -destroy_client(client_data) - svc_rpc_gss_data *client_data; +destroy_client(svc_rpc_gss_data *client_data) { OM_uint32 minor; int index = HASH(client_data->key); @@ -1690,20 +1687,20 @@ destroy_client(client_data) */ if (client_data->context != GSS_C_NO_CONTEXT) { (void) kgss_delete_sec_context(&minor, &client_data->context, - NULL); + NULL); common_client_data_free(client_data); if (client_data->deleg != GSS_C_NO_CREDENTIAL) { - (void) kgss_release_cred(&minor, &client_data->deleg, - crgetuid(CRED())); + (void) kgss_release_cred(&minor, &client_data->deleg, + crgetuid(CRED())); } } if (client_data->u_cred.gidlist != NULL) { - kmem_free((char *)client_data->u_cred.gidlist, - client_data->u_cred.gidlen * sizeof (gid_t)); - client_data->u_cred.gidlist = NULL; + kmem_free((char *)client_data->u_cred.gidlist, + client_data->u_cred.gidlen * sizeof (gid_t)); + client_data->u_cred.gidlist = NULL; } if (client_data->retrans_data != NULL) retrans_del(client_data); @@ -1773,11 +1770,8 @@ sweep_clients(bool_t from_reclaim) * and write the result to xdrs. */ static bool_t -svc_rpc_gss_wrap(auth, out_xdrs, xdr_func, xdr_ptr) - SVCAUTH *auth; - XDR *out_xdrs; - bool_t (*xdr_func)(); - caddr_t xdr_ptr; +svc_rpc_gss_wrap(SVCAUTH *auth, XDR *out_xdrs, bool_t (*xdr_func)(), + caddr_t xdr_ptr) { svc_rpc_gss_parms_t *gss_parms = SVCAUTH_GSSPARMS(auth); bool_t ret; @@ -1787,15 +1781,14 @@ svc_rpc_gss_wrap(auth, out_xdrs, xdr_func, xdr_ptr) * privacy service is used, don't wrap - just XDR encode. * Otherwise, wrap data using service and QOP parameters. */ - if (!gss_parms->established || - gss_parms->service == rpc_gss_svc_none) + if (!gss_parms->established || gss_parms->service == rpc_gss_svc_none) return ((*xdr_func)(out_xdrs, xdr_ptr)); ret = __rpc_gss_wrap_data(gss_parms->service, - (OM_uint32)gss_parms->qop_rcvd, - (gss_ctx_id_t)gss_parms->context, - gss_parms->seq_num, - out_xdrs, xdr_func, xdr_ptr); + (OM_uint32)gss_parms->qop_rcvd, + (gss_ctx_id_t)gss_parms->context, + gss_parms->seq_num, + out_xdrs, xdr_func, xdr_ptr); return (ret); } @@ -1803,11 +1796,8 @@ svc_rpc_gss_wrap(auth, out_xdrs, xdr_func, xdr_ptr) * Decrypt the serialized arguments and XDR decode them. */ static bool_t -svc_rpc_gss_unwrap(auth, in_xdrs, xdr_func, xdr_ptr) - SVCAUTH *auth; - XDR *in_xdrs; - bool_t (*xdr_func)(); - caddr_t xdr_ptr; +svc_rpc_gss_unwrap(SVCAUTH *auth, XDR *in_xdrs, bool_t (*xdr_func)(), + caddr_t xdr_ptr) { svc_rpc_gss_parms_t *gss_parms = SVCAUTH_GSSPARMS(auth); @@ -1816,15 +1806,14 @@ svc_rpc_gss_unwrap(auth, in_xdrs, xdr_func, xdr_ptr) * privacy service is used, don't unwrap - just XDR decode. * Otherwise, unwrap data. */ - if (!gss_parms->established || - gss_parms->service == rpc_gss_svc_none) + if (!gss_parms->established || gss_parms->service == rpc_gss_svc_none) return ((*xdr_func)(in_xdrs, xdr_ptr)); return (__rpc_gss_unwrap_data(gss_parms->service, - (gss_ctx_id_t)gss_parms->context, - gss_parms->seq_num, - gss_parms->qop_rcvd, - in_xdrs, xdr_func, xdr_ptr)); + (gss_ctx_id_t)gss_parms->context, + gss_parms->seq_num, + gss_parms->qop_rcvd, + in_xdrs, xdr_func, xdr_ptr)); } diff --git a/usr/src/uts/common/rpc/svc.c b/usr/src/uts/common/rpc/svc.c index 43f8a6d703..9ea26934b5 100644 --- a/usr/src/uts/common/rpc/svc.c +++ b/usr/src/uts/common/rpc/svc.c @@ -20,7 +20,9 @@ */ /* + * Copyright 2012 Marcel Telka <marcel@telka.sk> * Copyright 2015 Nexenta Systems, Inc. All rights reserved. + * Copyright 2018 OmniOS Community Edition (OmniOSce) Association. */ /* @@ -33,7 +35,7 @@ */ /* Copyright (c) 1983, 1984, 1985, 1986, 1987, 1988, 1989 AT&T */ -/* All Rights Reserved */ +/* All Rights Reserved */ /* * Portions of this source code were derived from Berkeley 4.3 BSD @@ -296,27 +298,6 @@ static caddr_t rqcred_head; static kmutex_t rqcred_lock; /* - * Pointers to transport specific `rele' routines in rpcmod (set from rpcmod). - */ -void (*rpc_rele)(queue_t *, mblk_t *, bool_t) = NULL; -void (*mir_rele)(queue_t *, mblk_t *, bool_t) = NULL; - -/* ARGSUSED */ -void -rpc_rdma_rele(queue_t *q, mblk_t *mp, bool_t enable) -{ -} -void (*rdma_rele)(queue_t *, mblk_t *, bool_t) = rpc_rdma_rele; - - -/* - * This macro picks which `rele' routine to use, based on the transport type. - */ -#define RELE_PROC(xprt) \ - ((xprt)->xp_type == T_RDMA ? rdma_rele : \ - (((xprt)->xp_type == T_CLTS) ? rpc_rele : mir_rele)) - -/* * If true, then keep quiet about version mismatch. * This macro is for broadcast RPC only. We have no broadcast RPC in * kernel now but one may define a flag in the transport structure @@ -595,7 +576,7 @@ svc_pool_register(struct svc_globals *svc, SVCPOOL *pool, int id) */ static int svc_pool_init(SVCPOOL *pool, uint_t maxthreads, uint_t redline, - uint_t qsize, uint_t timeout, uint_t stksize, uint_t max_same_xprt) + uint_t qsize, uint_t timeout, uint_t stksize, uint_t max_same_xprt) { klwp_t *lwp = ttolwp(curthread); @@ -2387,7 +2368,7 @@ svc_run(SVCPOOL *pool) if (enable) xprt->xp_enable = FALSE; mutex_exit(&xprt->xp_req_lock); - (*RELE_PROC(xprt)) (clone_xprt->xp_wq, NULL, enable); + SVC_RELE(clone_xprt, NULL, enable); } /* NOTREACHED */ } @@ -2412,7 +2393,7 @@ svc_queueclean(queue_t *q) /* remove the request from the list */ xprt->xp_req_head = mp->b_next; mp->b_next = (mblk_t *)0; - (*RELE_PROC(xprt)) (xprt->xp_wq, mp, FALSE); + SVC_RELE(xprt, mp, FALSE); } mutex_enter(&pool->p_req_lock); @@ -2729,7 +2710,7 @@ svc_detach_thread(SVCXPRT *clone_xprt) if (enable) xprt->xp_enable = FALSE; mutex_exit(&xprt->xp_req_lock); - (*RELE_PROC(xprt)) (clone_xprt->xp_wq, NULL, enable); + SVC_RELE(clone_xprt, NULL, enable); /* Mark the clone (thread) as detached */ clone_xprt->xp_reserved = FALSE; diff --git a/usr/src/uts/common/rpc/svc.h b/usr/src/uts/common/rpc/svc.h index fadf6b2609..2ed1ce5e34 100644 --- a/usr/src/uts/common/rpc/svc.h +++ b/usr/src/uts/common/rpc/svc.h @@ -20,7 +20,9 @@ */ /* * Copyright (c) 1989, 2010, Oracle and/or its affiliates. All rights reserved. + * Copyright 2012 Marcel Telka <marcel@telka.sk> * Copyright 2013 Nexenta Systems, Inc. All rights reserved. + * Copyright 2018 OmniOS Community Edition (OmniOSce) Association. */ /* Copyright (c) 1983, 1984, 1985, 1986, 1987, 1988, 1989 AT&T */ /* All Rights Reserved */ @@ -189,7 +191,11 @@ struct svc_ops { /* `ready-to-receive' */ void (*xp_clone_xprt)(SVCXPRT *, SVCXPRT *); /* transport specific clone function */ - void (*xp_tattrs) (SVCXPRT *, int, void **); + void (*xp_tattrs)(SVCXPRT *, int, void **); + /* transport specific hold function */ + void (*xp_hold)(queue_t *); + /* transport specific release function */ + void (*xp_release)(queue_t *, mblk_t *, bool_t); }; #define SVC_TATTR_ADDRMASK 1 @@ -272,7 +278,7 @@ struct __svcpool { kmutex_t p_thread_lock; /* Thread lock */ int p_asleep; /* Asleep threads */ int p_drowsy; /* Drowsy flag */ - kcondvar_t p_req_cv; /* svc_poll() sleep var. */ + kcondvar_t p_req_cv; /* svc_poll() sleep var. */ clock_t p_timeout; /* svc_poll() timeout */ kmutex_t p_req_lock; /* Request lock */ int p_reqs; /* Pending requests */ @@ -414,8 +420,8 @@ typedef struct __svcxprt_common { #define xp_netid xp_xpc.xpc_netid struct __svcmasterxprt { - SVCMASTERXPRT *xp_next; /* Next transport in the list */ - SVCMASTERXPRT *xp_prev; /* Prev transport in the list */ + SVCMASTERXPRT *xp_next; /* Next transport in the list */ + SVCMASTERXPRT *xp_prev; /* Prev transport in the list */ __SVCXPRT_COMMON xp_xpc; /* Fields common with the clone */ SVCPOOL *xp_pool; /* Pointer to the pool */ mblk_t *xp_req_head; /* Request queue head */ @@ -532,6 +538,14 @@ struct __svcxprt { (*(src_xprt)->xp_ops->xp_clone_xprt) \ (src_xprt, dst_xprt) +#define SVC_HOLD(xprt) \ + if ((xprt)->xp_ops->xp_hold) \ + (*(xprt)->xp_ops->xp_hold)((xprt)->xp_wq) + +#define SVC_RELE(xprt, mp, enable) \ + if ((xprt)->xp_ops->xp_release) \ + (*(xprt)->xp_ops->xp_release)((xprt)->xp_wq, (mp), (enable)) + #define SVC_RECV(clone_xprt, mp, msg) \ (*(clone_xprt)->xp_ops->xp_recv)((clone_xprt), (mp), (msg)) @@ -728,6 +742,15 @@ extern void xprt_unregister(); #endif /* __STDC__ */ #endif /* _KERNEL */ +#ifdef _KERNEL +/* + * Transport hold and release. + */ +extern void rpcmod_hold(queue_t *); +extern void rpcmod_release(queue_t *, mblk_t *, bool_t); +extern void mir_svc_hold(queue_t *); +extern void mir_svc_release(queue_t *, mblk_t *, bool_t); +#endif /* _KERNEL */ /* * When the service routine is called, it must first check to see if it @@ -903,7 +926,7 @@ extern int svc_create(void (*)(struct svc_req *, SVCXPRT *), const rpcprog_t, const rpcvers_t, const char *); /* - * void (*dispatch)(); -- dispatch routine + * void (*dispatch)(); -- dispatch routine * const rpcprog_t prognum; -- program number * const rpcvers_t versnum; -- version number * const char *nettype; -- network type @@ -976,9 +999,9 @@ extern SVCXPRT *svc_dg_create(const int, const uint_t, const uint_t); */ extern SVCXPRT *svc_fd_create(const int, const uint_t, const uint_t); /* - * const int fd; -- open connection end point - * const uint_t sendsize; -- max send size - * const uint_t recvsize; -- max recv size + * const int fd; -- open connection end point + * const uint_t sendsize; -- max send size + * const uint_t recvsize; -- max recv size */ /* @@ -993,7 +1016,7 @@ extern SVCXPRT *svc_door_create(void (*)(struct svc_req *, SVCXPRT *), const rpcprog_t, const rpcvers_t, const uint_t); /* - * void (*dispatch)(); -- dispatch routine + * void (*dispatch)(); -- dispatch routine * const rpcprog_t prognum; -- program number * const rpcvers_t versnum; -- version number * const uint_t sendsize; -- send buffer size diff --git a/usr/src/uts/common/rpc/svc_clts.c b/usr/src/uts/common/rpc/svc_clts.c index cc161c1457..f38f8e85ed 100644 --- a/usr/src/uts/common/rpc/svc_clts.c +++ b/usr/src/uts/common/rpc/svc_clts.c @@ -21,12 +21,14 @@ /* * Copyright 2015 Nexenta Systems, Inc. All rights reserved. - * Copyright (c) 1989, 2010, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1989, 2010, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2012 by Delphix. All rights reserved. + * Copyright 2012 Marcel Telka <marcel@telka.sk> + * Copyright 2018 OmniOS Community Edition (OmniOSce) Association. */ /* Copyright (c) 1983, 1984, 1985, 1986, 1987, 1988, 1989 AT&T */ -/* All Rights Reserved */ +/* All Rights Reserved */ /* * Portions of this source code were derived from Berkeley 4.3 BSD @@ -101,7 +103,9 @@ struct svc_ops svc_clts_op = { svc_clts_kclone_destroy, /* Destroy a clone xprt */ svc_clts_kstart, /* Tell `ready-to-receive' to rpcmod */ svc_clts_kclone_xprt, /* transport specific clone xprt function */ - svc_clts_ktattrs /* Transport specific attributes. */ + svc_clts_ktattrs, /* Transport specific attributes */ + rpcmod_hold, /* Increment transport reference count */ + rpcmod_release /* Decrement transport reference count */ }; /* diff --git a/usr/src/uts/common/rpc/svc_cots.c b/usr/src/uts/common/rpc/svc_cots.c index d4e93b0002..6fda4ab4c2 100644 --- a/usr/src/uts/common/rpc/svc_cots.c +++ b/usr/src/uts/common/rpc/svc_cots.c @@ -21,12 +21,14 @@ /* * Copyright 2015 Nexenta Systems, Inc. All rights reserved. - * Copyright (c) 1993, 2010, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1993, 2010, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2012 by Delphix. All rights reserved. + * Copyright 2012 Marcel Telka <marcel@telka.sk> + * Copyright 2018 OmniOS Community Edition (OmniOSce) Association. */ /* Copyright (c) 1983, 1984, 1985, 1986, 1987, 1988, 1989 AT&T */ -/* All Rights Reserved */ +/* All Rights Reserved */ /* * Portions of this source code were derived from Berkeley 4.3 BSD @@ -104,7 +106,9 @@ struct svc_ops svc_cots_op = { svc_cots_kclone_destroy, /* Destroy a clone xprt */ svc_cots_kstart, /* Tell `ready-to-receive' to rpcmod */ NULL, /* Transport specific clone xprt */ - svc_cots_ktattrs /* Transport Attributes */ + svc_cots_ktattrs, /* Transport Attributes */ + mir_svc_hold, /* Increment transport reference count */ + mir_svc_release /* Decrement transport reference count */ }; /* diff --git a/usr/src/uts/common/rpc/svc_rdma.c b/usr/src/uts/common/rpc/svc_rdma.c index f4d6efde94..544955012b 100644 --- a/usr/src/uts/common/rpc/svc_rdma.c +++ b/usr/src/uts/common/rpc/svc_rdma.c @@ -22,6 +22,8 @@ * Copyright (c) 1983, 2010, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2012 by Delphix. All rights reserved. * Copyright 2013 Nexenta Systems, Inc. All rights reserved. + * Copyright 2012 Marcel Telka <marcel@telka.sk> + * Copyright 2018 OmniOS Community Edition (OmniOSce) Association. */ /* Copyright (c) 1983, 1984, 1985, 1986, 1987, 1988, 1989 AT&T */ /* All Rights Reserved */ @@ -82,7 +84,7 @@ uint32_t rdma_bufs_granted = RDMA_BUFS_GRANT; * RDMA transport specific data associated with SVCMASTERXPRT */ struct rdma_data { - SVCMASTERXPRT *rd_xprt; /* back ptr to SVCMASTERXPRT */ + SVCMASTERXPRT *rd_xprt; /* back ptr to SVCMASTERXPRT */ struct rdma_svc_data rd_data; /* rdma data */ rdma_mod_t *r_mod; /* RDMA module containing ops ptr */ }; @@ -148,7 +150,9 @@ struct svc_ops rdma_svc_ops = { svc_rdma_kclone_destroy, /* Destroy a clone xprt */ svc_rdma_kstart, /* Tell `ready-to-receive' to rpcmod */ svc_rdma_kclone_xprt, /* Transport specific clone xprt */ - svc_rdma_ktattrs /* Get Transport Attributes */ + svc_rdma_ktattrs, /* Get Transport Attributes */ + NULL, /* Increment transport reference count */ + NULL /* Decrement transport reference count */ }; /* |