⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 helper.cxx

📁 一个著名的SIP协议栈
💻 CXX
📖 第 1 页 / 共 5 页
字号:
#if defined(HAVE_CONFIG_H)
#include "resip/stack/config.hxx"
#endif

#include <string.h>
#include <iomanip>
#include <algorithm>
#include <memory>

#include "resip/stack/Auth.hxx"
#include "resip/stack/BasicNonceHelper.hxx"
#include "resip/stack/Helper.hxx"
#include "resip/stack/NonceHelper.hxx"
#include "rutil/Coders.hxx"
#include "resip/stack/Uri.hxx"
#include "rutil/Logger.hxx"
#include "rutil/Random.hxx"
#include "rutil/Timer.hxx"
#include "rutil/DataStream.hxx"
#include "rutil/MD5Stream.hxx"
#include "rutil/DnsUtil.hxx"
#include "rutil/compat.hxx"
#include "rutil/ParseBuffer.hxx"
#include "resip/stack/SipMessage.hxx"
#include "resip/stack/Security.hxx"
//#include "resip/stack/SecurityAttributes.hxx"
//#include "resip/stack/Contents.hxx"
#include "resip/stack/Pkcs7Contents.hxx"
#include "resip/stack/MultipartSignedContents.hxx"
#include "resip/stack/MultipartMixedContents.hxx"
#include "resip/stack/MultipartAlternativeContents.hxx"
#include "rutil/WinLeakCheck.hxx"

using namespace resip;
using namespace std;

#define RESIPROCATE_SUBSYSTEM Subsystem::SIP

const int Helper::tagSize = 4;

// !jf! this should be settable by the application in case a group of apps
// (e.g. proxies) want to share the same secret
Helper::NonceHelperPtr Helper::mNonceHelperPtr;

SipMessage*
Helper::makeRequest(const NameAddr& target, const NameAddr& from, const NameAddr& contact, MethodTypes method)
{
   SipMessage* request = new SipMessage;
   RequestLine rLine(method);
   rLine.uri() = target.uri();
   request->header(h_To) = target;
   request->header(h_RequestLine) = rLine;
   request->header(h_MaxForwards).value() = 70;
   request->header(h_CSeq).method() = method;
   request->header(h_CSeq).sequence() = 1;
   request->header(h_From) = from;
   request->header(h_From).param(p_tag) = Helper::computeTag(Helper::tagSize);
   request->header(h_Contacts).push_back(contact);
   request->header(h_CallId).value() = Helper::computeCallId();
   //request->header(h_ContentLength).value() = 0;
   
   Via via;
   request->header(h_Vias).push_back(via);
   
   return request;
}

SipMessage*
Helper::makeRequest(const NameAddr& target, const NameAddr& from, MethodTypes method)
{
   NameAddr contact;
   return makeRequest(target, from, contact, method);
}

SipMessage*
Helper::makeRegister(const NameAddr& to, const NameAddr& from)
{
   NameAddr contact;
   return makeRegister(to, from, contact);
}

SipMessage*
Helper::makeRegister(const NameAddr& to, const NameAddr& from, const NameAddr& contact)
{
   SipMessage* request = new SipMessage;
   RequestLine rLine(REGISTER);

   rLine.uri().scheme() = to.uri().scheme();
   rLine.uri().host() = to.uri().host();
   rLine.uri().port() = to.uri().port();
   if (to.uri().exists(p_transport))
   {
      rLine.uri().param(p_transport) = to.uri().param(p_transport);
   }

   request->header(h_To) = to;
   request->header(h_RequestLine) = rLine;
   request->header(h_MaxForwards).value() = 70;
   request->header(h_CSeq).method() = REGISTER;
   request->header(h_CSeq).sequence() = 1;
   request->header(h_From) = from;
   request->header(h_From).param(p_tag) = Helper::computeTag(Helper::tagSize);
   request->header(h_CallId).value() = Helper::computeCallId();
   assert(!request->exists(h_Contacts) || request->header(h_Contacts).empty());
   request->header(h_Contacts).push_back( contact );
   
   Via via;
   request->header(h_Vias).push_back(via);
   
   return request;
}

SipMessage*
Helper::makeRegister(const NameAddr& to,const Data& transport)
{
   NameAddr contact;
   return makeRegister(to, transport, contact);
   
}

SipMessage*
Helper::makeRegister(const NameAddr& to, const Data& transport, const NameAddr& contact)
{
   SipMessage* request = new SipMessage;
   RequestLine rLine(REGISTER);

   rLine.uri().scheme() = to.uri().scheme();
   rLine.uri().host() = to.uri().host();
   rLine.uri().port() = to.uri().port();
   if (!transport.empty())
   {
      rLine.uri().param(p_transport) = transport;
   }

   request->header(h_To) = to;
   request->header(h_RequestLine) = rLine;
   request->header(h_MaxForwards).value() = 70;
   request->header(h_CSeq).method() = REGISTER;
   request->header(h_CSeq).sequence() = 1;
   request->header(h_From) = to;
   request->header(h_From).param(p_tag) = Helper::computeTag(Helper::tagSize);
   request->header(h_CallId).value() = Helper::computeCallId();
   assert(!request->exists(h_Contacts) || request->header(h_Contacts).empty());
   request->header(h_Contacts).push_back( contact );
   
   Via via;
   request->header(h_Vias).push_back(via);
   
   return request;
}


SipMessage*
Helper::makePublish(const NameAddr& target, const NameAddr& from)
{
   NameAddr contact;
   return makePublish(target, from, contact);
}

SipMessage*
Helper::makePublish(const NameAddr& target, const NameAddr& from, const NameAddr& contact)
{
   SipMessage* request = new SipMessage;
   RequestLine rLine(PUBLISH);
   rLine.uri() = target.uri();

   request->header(h_To) = target;
   request->header(h_RequestLine) = rLine;
   request->header(h_MaxForwards).value() = 70;
   request->header(h_CSeq).method() = PUBLISH;
   request->header(h_CSeq).sequence() = 1;
   request->header(h_From) = from;
   request->header(h_From).param(p_tag) = Helper::computeTag(Helper::tagSize);
   request->header(h_CallId).value() = Helper::computeCallId();
   assert(!request->exists(h_Contacts) || request->header(h_Contacts).empty());
   request->header(h_Contacts).push_back( contact );
   Via via;
   request->header(h_Vias).push_back(via);
   
   return request;
}

SipMessage*
Helper::makeMessage(const NameAddr& target, const NameAddr& from)
{
   NameAddr contact;
   return makeMessage(target, from, contact);
}

SipMessage*
Helper::makeMessage(const NameAddr& target, const NameAddr& from, const NameAddr& contact)
{
   SipMessage* request = new SipMessage;
   RequestLine rLine(MESSAGE);
   rLine.uri() = target.uri();

   request->header(h_To) = target;
   request->header(h_RequestLine) = rLine;
   request->header(h_MaxForwards).value() = 70;
   request->header(h_CSeq).method() = MESSAGE;
   request->header(h_CSeq).sequence() = 1;
   request->header(h_From) = from;
   request->header(h_From).param(p_tag) = Helper::computeTag(Helper::tagSize);
   request->header(h_CallId).value() = Helper::computeCallId();
   assert(!request->exists(h_Contacts) || request->header(h_Contacts).empty());
   request->header(h_Contacts).push_back( contact );
   Via via;
   request->header(h_Vias).push_back(via);
   
   return request;
}


SipMessage*
Helper::makeSubscribe(const NameAddr& target, const NameAddr& from)
{
   NameAddr contact;
   return makeSubscribe(target, from, contact);
}

SipMessage*
Helper::makeSubscribe(const NameAddr& target, const NameAddr& from, const NameAddr& contact)
{
   SipMessage* request = new SipMessage;
   RequestLine rLine(SUBSCRIBE);
   rLine.uri() = target.uri();

   request->header(h_To) = target;
   request->header(h_RequestLine) = rLine;
   request->header(h_MaxForwards).value() = 70;
   request->header(h_CSeq).method() = SUBSCRIBE;
   request->header(h_CSeq).sequence() = 1;
   request->header(h_From) = from;
   request->header(h_From).param(p_tag) = Helper::computeTag(Helper::tagSize);
   request->header(h_CallId).value() = Helper::computeCallId();
   assert(!request->exists(h_Contacts) || request->header(h_Contacts).empty());
   request->header(h_Contacts).push_front( contact );
   Via via;
   request->header(h_Vias).push_front(via);
   
   return request;
}

int
Helper::jitterValue(int input, int lowerPercentage, int upperPercentage, int minimum)
{
   assert(upperPercentage >= lowerPercentage);
   if (input < minimum)
   {
      return input;
   }
   else if (lowerPercentage == 100 && upperPercentage == 100)
   {
      return input;
   }
   else
   {
      const int rnd = Random::getRandom() % (upperPercentage-lowerPercentage) + lowerPercentage;
      return (input * rnd) / 100;
   }
}

SipMessage*
Helper::makeInvite(const NameAddr& target, const NameAddr& from)
{
   return Helper::makeRequest(target, from, INVITE);
}

SipMessage*
Helper::makeInvite(const NameAddr& target, const NameAddr& from, const NameAddr& contact)
{
   return Helper::makeRequest(target, from, contact, INVITE);
}


void
Helper::makeResponse(SipMessage& response, 
                     const SipMessage& request, 
                     int responseCode, 
                     const NameAddr& myContact, 
                     const Data& reason,
                     const Data& hostname,
                     const Data& warning)
{
   makeResponse(response,request, responseCode, reason,hostname, warning);
   // in general, this should not create a Contact header since only requests
   // that create a dialog (or REGISTER requests) should produce a response with
   // a contact(s). 
   response.header(h_Contacts).clear();
   response.header(h_Contacts).push_back(myContact);
}


void
Helper::makeResponse(SipMessage& response, 
                     const SipMessage& request, 
                     int responseCode, 
                     const Data& reason,
                     const Data& hostname,
                     const Data& warning)
{
   DebugLog(<< "Helper::makeResponse(" << request.brief() << " code=" << responseCode << " reason=" << reason);
   response.header(h_StatusLine).responseCode() = responseCode;
   response.header(h_From) = request.header(h_From);
   response.header(h_To) = request.header(h_To);
   response.header(h_CallId) = request.header(h_CallId);
   response.header(h_CSeq) = request.header(h_CSeq);
   response.header(h_Vias) = request.header(h_Vias);

   if (!warning.empty())
   {
      WarningCategory warn;
      warn.code() = 499;
      warn.hostname() = hostname;
      warn.text() = warning;
      response.header(h_Warnings).push_back(warn);
   }

   try
   {
      // Only generate a To: tag if one doesn't exist.  Think Re-INVITE.   
      // No totag for failure responses or 100s   
      if (!response.header(h_To).exists(p_tag) && responseCode > 100)   
      {   
         response.header(h_To).param(p_tag) = Helper::computeTag(Helper::tagSize);   
      }
   } 
   catch(resip::ParseBuffer::Exception&)
   {
      // !bwc! Can't add to-tag since To is malformed. Oh well, we tried.
   }
   
   response.setRFC2543TransactionId(request.getRFC2543TransactionId());
   //response.header(h_ContentLength).value() = 0;
   
   if (responseCode >= 180 && responseCode < 300 && request.exists(h_RecordRoutes))
   {
      response.header(h_RecordRoutes) = request.header(h_RecordRoutes);
   }

   // !bwc! If CSeq is malformed, basicCheck would have already attempted to
   // parse it, meaning we won't throw here (we never try to parse the same
   // thing twice, see LazyParser::checkParsed())
   if (responseCode/100 == 2 &&
         !response.exists(h_Contacts) &&
         !(response.header(h_CSeq).method()==CANCEL) )
   {
      // in general, this should not create a Contact header since only requests
      // that create a dialog (or REGISTER requests) should produce a response with
      // a contact(s). 
      
      NameAddr contact;
      response.header(h_Contacts).push_back(contact);
   }

   if (request.isExternal())
   {
       response.setFromTU();
   }
   else
   {
       response.setFromExternal();
   }

   if (reason.size())
   {
      response.header(h_StatusLine).reason() = reason;
   }
   else
   {
      getResponseCodeReason(responseCode, response.header(h_StatusLine).reason());
   }
}

SipMessage*
Helper::makeResponse(const SipMessage& request, 
                     int responseCode, 
                     const NameAddr& myContact, 
                     const Data& reason, 
                     const Data& hostname, 
                     const Data& warning)
{
   // !bwc! Exception safety. Catch/rethrow is dicey because we can't rethrow
   // resip::BaseException, since it is abstract.
   std::auto_ptr<SipMessage> response(new SipMessage);

   makeResponse(*response, request, responseCode, reason, hostname, warning);

   // in general, this should not create a Contact header since only requests
   // that create a dialog (or REGISTER requests) should produce a response with
   // a contact(s). 
   response->header(h_Contacts).clear();
   response->header(h_Contacts).push_back(myContact);
   return response.release();
}


SipMessage*
Helper::makeResponse(const SipMessage& request, 

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -