osaf/libs/agents/saf/imma/imma_proc.c | 37 ++++++++++++++++++++++++++-- osaf/libs/common/immsv/immsv_evt.c | 8 ++++- osaf/libs/common/immsv/include/immsv_evt.h | 1 + osaf/services/saf/immsv/immnd/ImmModel.cc | 38 ++++++++++++++++++----------- osaf/services/saf/immsv/immnd/ImmModel.hh | 3 +- osaf/services/saf/immsv/immnd/immnd_evt.c | 12 +++++++-- osaf/services/saf/immsv/immnd/immnd_init.h | 2 +- 7 files changed, 77 insertions(+), 24 deletions(-)
Same fix as for the create and modify callbacks but here for delete-cb. The only thing relevant for the delete callback is the object DN. The IMMND server will screen the DN of every ccbObjectDelete for having a long DN. If this is detected, then the message sent to the client (for the callback) will be a new node local message type. This is also relevant to protect incapable appliers even if the OI is capable. The new message type conveys the same semantics as the old delete-callback message type but adds the information that the callback has a DN that is not compatible with an OI that is not long DN capable. The imma library uses this fact to check if the client is long DN capable. If not it does not generate the callback. Instead the library bounces internally with error directly to the server. The CCB will fail (get aborted). For appliers, the dispatch loop is broken and the handle is invalidated. This is necessary because the applier can not reply to the server. If the main OI is long DN capable, or there is no main OI, then the CCB can succeed in commit, yet the delete callback never reaches the applier. To avoid a silent breach of contract with such an applier, the handle is stale-marked and BAD_HANDLE returned to the applier. diff --git a/osaf/libs/agents/saf/imma/imma_proc.c b/osaf/libs/agents/saf/imma/imma_proc.c --- a/osaf/libs/agents/saf/imma/imma_proc.c +++ b/osaf/libs/agents/saf/imma/imma_proc.c @@ -975,7 +975,7 @@ static void imma_proc_ccb_abort(IMMA_CB evt - IMMA_EVT. Return Values : None ******************************************************************************/ -static void imma_proc_obj_delete(IMMA_CB *cb, IMMA_EVT *evt) +static void imma_proc_obj_delete(IMMA_CB *cb, bool hasLongDn, IMMA_EVT *evt) { IMMA_CALLBACK_INFO *callback; IMMA_CLIENT_NODE *cl_node = NULL; @@ -1021,6 +1021,10 @@ static void imma_proc_obj_delete(IMMA_CB evt->info.objDelete.objectName.buf = NULL; evt->info.objDelete.objectName.size = 0; + if(hasLongDn) { + callback->hasLongRdnOrDn = true; + } + /* Send the event */ (void)m_NCS_IPC_SEND(&cl_node->callbk_mbx, callback, NCS_IPC_PRIORITY_NORMAL); TRACE("Posted IMMA_CALLBACK_OI_CCB_DELETE for ccb %u", evt->info.objDelete.ccbId); @@ -1299,6 +1303,7 @@ void imma_proc_free_pointers(IMMA_CB *cb break; case IMMA_EVT_ND2A_OI_OBJ_DELETE_UC: + case IMMA_EVT_ND2A_OI_OBJ_DELETE_LONG_UC: free(evt->info.objDelete.objectName.buf); evt->info.objDelete.objectName.buf = NULL; evt->info.objDelete.objectName.size = 0; @@ -1361,8 +1366,12 @@ void imma_process_evt(IMMA_CB *cb, IMMSV imma_proc_obj_create(cb, false, &evt->info.imma); break; + case IMMA_EVT_ND2A_OI_OBJ_DELETE_LONG_UC: + imma_proc_obj_delete(cb, true, &evt->info.imma); + break; + case IMMA_EVT_ND2A_OI_OBJ_DELETE_UC: - imma_proc_obj_delete(cb, &evt->info.imma); + imma_proc_obj_delete(cb, false, &evt->info.imma); break; case IMMA_EVT_ND2A_OI_OBJ_MODIFY_UC: @@ -2441,10 +2450,32 @@ static bool imma_process_callback_info(I if(!(cl_node->isApplier)) {imma_oi_ccb_allow_error_string(cl_node, ccbid);} } - if (osaf_is_extended_name_valid(&(callback->name))) { + if(!osaf_is_extended_names_enabled() && (callback->hasLongRdnOrDn)) { + /* (callback->hasLongRdnOrDn) set above at '$$$$' here means + that the delete callback has a long DN. + This property is not compatible for a client that does not + support long DNs. This case is detected in the server + and communicated here to the generic client code. + */ + TRACE_3("Extended names not enabled. DN(%zu) too long. ccb: %u", + strlen(osaf_extended_name_borrow(&(callback->name))), callback->ccbID); + localEr = SA_AIS_ERR_BAD_OPERATION; + if(cl_node->isApplier) { + /* We cannot uphold the contract for an applier that is not long DN + capable. For regular OI this is not a problem since an error can + be returned to the server aborting the CCB. But appliers can not + reply. If the OI/OIs are capable but some applier(s) are not then + we have a problem for those appliers. We can not just silently skip + the applier callback while the CCB goes on to commit. Instead we + break the dispatch loop. + */ + clientCapable = false; + } + } else if (osaf_is_extended_name_valid(&(callback->name))) { localEr = cl_node->o.iCallbk.saImmOiCcbObjectDeleteCallback(callback->lcl_imm_hdl, ccbid, &(callback->name)); } else { + /* We should not get here. */ if (osaf_is_extended_names_enabled()) { TRACE_3("Object name is too long: %s", osaf_extended_name_borrow(&(callback->name))); } else { diff --git a/osaf/libs/common/immsv/immsv_evt.c b/osaf/libs/common/immsv/immsv_evt.c --- a/osaf/libs/common/immsv/immsv_evt.c +++ b/osaf/libs/common/immsv/immsv_evt.c @@ -1439,7 +1439,8 @@ static uint32_t immsv_evt_enc_sublevels( LOG_ER("TOO MANY attribute modifications line:%u", __LINE__); return NCSCC_RC_OUT_OF_MEM; } - } else if (i_evt->info.imma.type == IMMA_EVT_ND2A_OI_OBJ_DELETE_UC) { + } else if ((i_evt->info.imma.type == IMMA_EVT_ND2A_OI_OBJ_DELETE_UC) || + (i_evt->info.imma.type == IMMA_EVT_ND2A_OI_OBJ_DELETE_LONG_UC)) { /*Encode the objectName */ IMMSV_OCTET_STRING *os = &(i_evt->info.imma.info.objDelete.objectName); if(!immsv_evt_enc_inline_text(__LINE__, o_ub, os)) { @@ -2106,7 +2107,8 @@ static uint32_t immsv_evt_dec_sublevels( immsv_evt_dec_attrmods(i_ub, &p); o_evt->info.imma.info.objModify.attrMods = p; } - } else if (o_evt->info.imma.type == IMMA_EVT_ND2A_OI_OBJ_DELETE_UC) { + } else if ((o_evt->info.imma.type == IMMA_EVT_ND2A_OI_OBJ_DELETE_UC) || + (o_evt->info.imma.type == IMMA_EVT_ND2A_OI_OBJ_DELETE_LONG_UC)) { /*Decode the objectName */ IMMSV_OCTET_STRING *os = &(o_evt->info.imma.info.objDelete.objectName); immsv_evt_dec_inline_string(i_ub, os); @@ -2767,6 +2769,7 @@ static uint32_t immsv_evt_enc_toplevel(I break; case IMMA_EVT_ND2A_OI_OBJ_DELETE_UC: //OBJ DELETE UP-CALL. + case IMMA_EVT_ND2A_OI_OBJ_DELETE_LONG_UC: IMMSV_RSRV_SPACE_ASSERT(p8, o_ub, 4); ncs_encode_32bit(&p8, immaevt->info.objDelete.ccbId); ncs_enc_claim_space(o_ub, 4); @@ -4137,6 +4140,7 @@ static uint32_t immsv_evt_dec_toplevel(N break; case IMMA_EVT_ND2A_OI_OBJ_DELETE_UC: //OBJ DELETE UP-CALL. + case IMMA_EVT_ND2A_OI_OBJ_DELETE_LONG_UC: IMMSV_FLTN_SPACE_ASSERT(p8, local_data, i_ub, 4); immaevt->info.objDelete.ccbId = ncs_decode_32bit(&p8); ncs_dec_skip_space(i_ub, 4); diff --git a/osaf/libs/common/immsv/include/immsv_evt.h b/osaf/libs/common/immsv/include/immsv_evt.h --- a/osaf/libs/common/immsv/include/immsv_evt.h +++ b/osaf/libs/common/immsv/include/immsv_evt.h @@ -92,6 +92,7 @@ typedef enum imma_evt_type { IMMA_EVT_ND2A_ACCESSOR_GET_RSP = 30, /* Response from accessorGet */ IMMA_EVT_ND2A_OI_OBJ_CREATE_LONG_UC = 31, /*OBJ CREATE UP-CALL with long DN. */ IMMA_EVT_ND2A_OI_OBJ_MODIFY_LONG_UC = 32, /*OBJ MODIFY UP-CALL with long DN. */ + IMMA_EVT_ND2A_OI_OBJ_DELETE_LONG_UC = 33, /*OBJ DELETE UP-CALL with long DN. */ IMMA_EVT_MAX } IMMA_EVT_TYPE; diff --git a/osaf/services/saf/immsv/immnd/ImmModel.cc b/osaf/services/saf/immsv/immnd/ImmModel.cc --- a/osaf/services/saf/immsv/immnd/ImmModel.cc +++ b/osaf/services/saf/immsv/immnd/ImmModel.cc @@ -752,7 +752,8 @@ immModel_ccbObjectDelete(IMMND_CB *cb, SaStringT** objNameArr, SaUint32T* pbeConn, SaClmNodeIdT* pbeNodeId, - bool* augDelete) + bool* augDelete, + bool* hasLongDn) { ConnVector cv; @@ -765,7 +766,7 @@ immModel_ccbObjectDelete(IMMND_CB *cb, SaAisErrorT err = ImmModel::instance(&cb->immModel)->ccbObjectDelete(req, - reqConn, ov, cv, iv, pbeConn, pbeNodeId, augDelete); + reqConn, ov, cv, iv, pbeConn, pbeNodeId, augDelete, hasLongDn); *arrSize = (SaUint32T) cv.size(); osafassert(*arrSize == iv.size()); osafassert(*arrSize == ov.size()); @@ -1583,9 +1584,9 @@ immModel_ccbCompletedContinuation(IMMND_ void immModel_ccbObjDelContinuation(IMMND_CB *cb, struct immsv_oi_ccb_upcall_rsp* rsp, - SaUint32T* reqConn, bool* augDelete) -{ - ImmModel::instance(&cb->immModel)->ccbObjDelContinuation(rsp, reqConn, augDelete); + SaUint32T* reqConn, bool* augDelete) +{ + ImmModel::instance(&cb->immModel)->ccbObjDelContinuation(rsp, reqConn, augDelete); } void @@ -8580,9 +8581,15 @@ ImmModel::ccbObjectDelete(const ImmsvOmC IdVector& continuations, SaUint32T* pbeConnPtr, unsigned int* pbeNodeIdPtr, - bool* augDelete) -{ - TRACE_ENTER(); + bool* augDelete, + bool* hasLongDn) + +{ + TRACE_ENTER(); + osafassert(augDelete); + *augDelete=false; + osafassert(hasLongDn); + *hasLongDn=false; SaAisErrorT err = SA_AIS_OK; //osafassert(!immNotWritable()); @@ -8603,12 +8610,15 @@ ImmModel::ccbObjectDelete(const ImmsvOmC ObjectMap::iterator oi, oi2; ObjectInfo* deleteRoot=NULL; - if(!getLongDnsAllowed() - && sz >= SA_MAX_UNEXTENDED_NAME_LENGTH) { - LOG_NO("ERR_NAME_TOO_LONG: Object name is too long. " - "Not allowed by IMM service or extended names are disabled"); - err = SA_AIS_ERR_NAME_TOO_LONG; - goto ccbObjectDeleteExit; + if(sz >= SA_MAX_UNEXTENDED_NAME_LENGTH) { + if(getLongDnsAllowed()) { + *hasLongDn = true; + } else { + LOG_NO("ERR_NAME_TOO_LONG: Object name is too long. " + "Not allowed by IMM service or extended names are disabled"); + err = SA_AIS_ERR_NAME_TOO_LONG; + goto ccbObjectDeleteExit; + } } if(! (nameCheck(objectName)||nameToInternal(objectName)) ) { diff --git a/osaf/services/saf/immsv/immnd/ImmModel.hh b/osaf/services/saf/immsv/immnd/ImmModel.hh --- a/osaf/services/saf/immsv/immnd/ImmModel.hh +++ b/osaf/services/saf/immsv/immnd/ImmModel.hh @@ -253,7 +253,8 @@ public: IdVector& continuations, SaUint32T* pbeConn, unsigned int* pbeNodeId, - bool* augDelete); + bool* augDelete, + bool* hasLongDn); SaAisErrorT deleteObject( ObjectMap::iterator& oi, diff --git a/osaf/services/saf/immsv/immnd/immnd_evt.c b/osaf/services/saf/immsv/immnd/immnd_evt.c --- a/osaf/services/saf/immsv/immnd/immnd_evt.c +++ b/osaf/services/saf/immsv/immnd/immnd_evt.c @@ -6706,6 +6706,7 @@ static void immnd_evt_proc_object_delete NCS_NODE_ID pbeNodeId = 0; NCS_NODE_ID *pbeNodeIdPtr = NULL; bool augDelete=false; + bool hasLongDn=false; TRACE_ENTER(); #if 0 /*ABT DEBUG PRINTOUTS START */ @@ -6722,7 +6723,7 @@ static void immnd_evt_proc_object_delete err = immModel_ccbObjectDelete(cb, &(evt->info.objDelete), originatedAtThisNd ? conn : 0, &arrSize, &implConnArr, &invocArr, &objNameArr, - &pbeConn, pbeNodeIdPtr, &augDelete); + &pbeConn, pbeNodeIdPtr, &augDelete, &hasLongDn); /* Before generating implementer upcalls for any local implementers, @@ -6741,6 +6742,7 @@ static void immnd_evt_proc_object_delete implHandle = m_IMMSV_PACK_HANDLE(pbeConn, pbeNodeId); memset(&send_evt, '\0', sizeof(IMMSV_EVT)); send_evt.type = IMMSV_EVT_TYPE_IMMA; + /* PBE is internal => can handle long DNs */ send_evt.info.imma.type = IMMA_EVT_ND2A_OI_OBJ_DELETE_UC; send_evt.info.imma.info.objDelete.ccbId = evt->info.objDelete.ccbId; send_evt.info.imma.info.objDelete.immHandle = implHandle; @@ -6795,7 +6797,8 @@ static void immnd_evt_proc_object_delete /*We have local implementer(s) for deleted object(s) */ memset(&send_evt, '\0', sizeof(IMMSV_EVT)); send_evt.type = IMMSV_EVT_TYPE_IMMA; - send_evt.info.imma.type = IMMA_EVT_ND2A_OI_OBJ_DELETE_UC; + send_evt.info.imma.type = hasLongDn ? + IMMA_EVT_ND2A_OI_OBJ_DELETE_LONG_UC : IMMA_EVT_ND2A_OI_OBJ_DELETE_UC; send_evt.info.imma.info.objDelete.ccbId = evt->info.objDelete.ccbId; int ix = 0; for (; ix < arrSize && err == SA_AIS_OK; ++ix) { @@ -6858,7 +6861,8 @@ static void immnd_evt_proc_object_delete /* Generate applier delete upcalls. */ memset(&send_evt, '\0', sizeof(IMMSV_EVT)); send_evt.type = IMMSV_EVT_TYPE_IMMA; - send_evt.info.imma.type = IMMA_EVT_ND2A_OI_OBJ_DELETE_UC; + send_evt.info.imma.type = hasLongDn ? IMMA_EVT_ND2A_OI_OBJ_DELETE_LONG_UC : + IMMA_EVT_ND2A_OI_OBJ_DELETE_UC; send_evt.info.imma.info.objDelete.ccbId = evt->info.objDelete.ccbId; send_evt.info.imma.info.objDelete.adminOwnerId = 0; /* Re-use the adminOwner member of the ccbDelete message to hold the @@ -7057,6 +7061,7 @@ static void immnd_evt_proc_rt_object_del implHandle = m_IMMSV_PACK_HANDLE(pbeConn, pbeNodeId); memset(&send_evt, '\0', sizeof(IMMSV_EVT)); send_evt.type = IMMSV_EVT_TYPE_IMMA; + /* PBE is internal => can handle long DNs */ send_evt.info.imma.type = IMMA_EVT_ND2A_OI_OBJ_DELETE_UC; send_evt.info.imma.info.objDelete.ccbId = 0; send_evt.info.imma.info.objDelete.adminOwnerId = continuationId; @@ -7137,6 +7142,7 @@ static void immnd_evt_proc_rt_object_del memset(&send_evt, '\0', sizeof(IMMSV_EVT)); send_evt.type = IMMSV_EVT_TYPE_IMMA; + send_evt.info.imma.type = IMMA_EVT_ND2A_OI_OBJ_DELETE_UC; send_evt.info.imma.info.objDelete.ccbId = 0; send_evt.info.imma.info.objDelete.adminOwnerId = continuationId; diff --git a/osaf/services/saf/immsv/immnd/immnd_init.h b/osaf/services/saf/immsv/immnd/immnd_init.h --- a/osaf/services/saf/immsv/immnd/immnd_init.h +++ b/osaf/services/saf/immsv/immnd/immnd_init.h @@ -156,7 +156,7 @@ extern "C" { immModel_ccbObjectDelete(IMMND_CB *cb, const struct ImmsvOmCcbObjectDelete *req, SaUint32T reqConn, SaUint32T *arrSize, SaUint32T **implConnArr, SaUint32T **implIdArr, - SaStringT **objNameArr, SaUint32T *pbeConn, SaClmNodeIdT *pbeNodeId, bool* augDelete); + SaStringT **objNameArr, SaUint32T *pbeConn, SaClmNodeIdT *pbeNodeId, bool* augDelete, bool* hasLongDn); SaAisErrorT ------------------------------------------------------------------------------ Comprehensive Server Monitoring with Site24x7. Monitor 10 servers for $9/Month. Get alerted through email, SMS, voice calls or mobile push notifications. Take corrective actions from your mobile device. http://pubads.g.doubleclick.net/gampad/clk?id=154624111&iu=/4140/ostg.clktrk _______________________________________________ Opensaf-devel mailing list Opensaf-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/opensaf-devel