X-Git-Url: https://git.teslayout.com/public/public/public/?a=blobdiff_plain;f=source%2Fdiameter%2Fcodec%2FAvp.cpp;h=17ba00520cc78e2c250ce30c104e99ec168f1bec;hb=42f606f1c76bfbef24e7e772b6939d69d5ea970e;hp=97437c1b40ed8fe4a5e2c59470f3f868c53139d0;hpb=e7dbacff41163bf8cefb267daae84d96056ebc86;p=anna.git diff --git a/source/diameter/codec/Avp.cpp b/source/diameter/codec/Avp.cpp index 97437c1..17ba005 100644 --- a/source/diameter/codec/Avp.cpp +++ b/source/diameter/codec/Avp.cpp @@ -687,7 +687,6 @@ void Avp::decodeDataPart(const char * buffer, int size, const parent_t & parent, int avpPos = 0; Avp* avp; anna::DataBlock db; - // Me as parent: parent_t me = parent; me.addAvp(a_id); @@ -786,13 +785,12 @@ void Avp::decode(const anna::DataBlock &db, const parent_t & parent, Message *an // a Diameter client, server, proxy, or translation agent and either the AVP or its value is unrecognized, the message MUST be rejected. // Diameter Relay and redirect agents MUST NOT reject messages with unrecognized AVPs. if(!getStackAvp() && mandatoryBit()) { + if(answer) { + answer->setResultCode(helpers::base::AVPVALUES__Result_Code::DIAMETER_AVP_UNSUPPORTED); + answer->setFailedAvp(parent, a_id); + } - if(answer) { - answer->setResultCode(helpers::base::AVPVALUES__Result_Code::DIAMETER_AVP_UNSUPPORTED); - answer->setFailedAvp(parent, a_id); - } - - unknownAvpWithMandatoryBit(); + unknownAvpWithMandatoryBit(); } // Avp Length @@ -1318,9 +1316,8 @@ std::string Avp::getXMLdata(bool & isHex, const stack::Format *stackFormat) cons //---------------------------------------------------------------- Avp::decode() //------------------------------------------------------------------------------ void Avp::decode(const anna::DataBlock &db) throw(anna::RuntimeException) { - parent_t parent; - parent.setMessage(CommandId(0,false), "No-Parent"); + parent.setMessage(CommandId(0, false), "No-Parent"); decode(db, parent, NULL); } @@ -1363,13 +1360,33 @@ void Avp::fromXML(const anna::xml::Node* avpNode) throw(anna::RuntimeException) // Check attributes exclusiveness if(name) { // compact mode - if(code || flags || vendorCode) { + bool allowFlagsField = ( stackAvp->getVbit() == anna::diameter::stack::Avp::FlagRule::may || stackAvp->getVbit() == anna::diameter::stack::Avp::FlagRule::shouldnot + || stackAvp->getMbit() == anna::diameter::stack::Avp::FlagRule::may || stackAvp->getMbit() == anna::diameter::stack::Avp::FlagRule::shouldnot + /* umm, perhaps we could omit for bit P, whic is deprecated ... */ + /* || stackAvp->getPbit() == anna::diameter::stack::Avp::FlagRule::may || stackAvp->getPbit() == anna::diameter::stack::Avp::FlagRule::shouldnot*/ ); + if(code || (flags && !allowFlagsField) || vendorCode) { std::string msg = "Error processing avp getValue(); - msg += "'>: avp attributes <'code' + 'flags' + 'vendorCode'> are not allowed if <'name'> is provided"; + if (flags) msg += "'>: avp attributes <'code' + 'flags' + 'vendorCode'> are not allowed if <'name'> is provided (also flags is not permitted: no may, no shouldnot)"; + else msg += "'>: avp attributes <'code' + 'vendorCode'> are not allowed if <'name'> is provided"; throw anna::RuntimeException(msg, ANNA_FILE_LOCATION); } setId(stackAvp->getId()); + + if (flags && allowFlagsField) { + // Flags check + int i_aux = flags->getIntegerValue(); + + if(i_aux < 0 || i_aux > 256) { + std::string msg = "Error processing avp getValue(); + msg += "': out of range [0,256]"; + throw anna::RuntimeException(msg, ANNA_FILE_LOCATION); + } + + a_flags = i_aux; + } + + } else { if(!code || !flags || !vendorCode) { std::string s_code = code ? code->getValue() : "?"; @@ -1568,6 +1585,12 @@ anna::xml::Node* Avp::asXML(anna::xml::Node* parent) const throw() { if(compactMode) { result->createAttribute("name", stackAvp->getName()); + // If may or shouldnot is present in AVP definition, we have to show flags to avoid uncertainty + if ( stackAvp->getVbit() == anna::diameter::stack::Avp::FlagRule::may || stackAvp->getVbit() == anna::diameter::stack::Avp::FlagRule::shouldnot + || stackAvp->getMbit() == anna::diameter::stack::Avp::FlagRule::may || stackAvp->getMbit() == anna::diameter::stack::Avp::FlagRule::shouldnot + /* umm, perhaps we could omit for bit P, whic is deprecated ... */ + /* || stackAvp->getPbit() == anna::diameter::stack::Avp::FlagRule::may || stackAvp->getPbit() == anna::diameter::stack::Avp::FlagRule::shouldnot*/ ) + result->createAttribute("flags", (int)a_flags); } else { result->createAttribute("code", a_id.first); result->createAttribute("vendor-code", a_id.second);