示例#1
0
   void testNoHooks()
      {
         OsConfigDb configuration;

         configuration.set("NOHOOKS_NOTPASSED_HOOK_LIBRARY.Error", PLUGIN_LIB_DIR "libfoo" PLUGIN_EXT);
         configuration.set("NOHOOKS_OTHERPARAM", "DummyValue");

         // there are no hooks configured for this prefix
         PluginHooks testPlugins("getTestPlugin", "NOHOOKS_PASSED");
         testPlugins.readConfig(configuration);

         PluginIterator shouldBeEmpty(testPlugins);

         UtlString name;

         // confirm that there are no hooks configured.
         CPPUNIT_ASSERT(shouldBeEmpty.next(&name) == NULL);
         CPPUNIT_ASSERT(name.isNull());

         CPPUNIT_ASSERT(shouldBeEmpty.next() == NULL);
      }
示例#2
0
UtlBoolean SipDialog::isTransactionRemotelyInitiated(const UtlString& callId,
                                                     const UtlString& fromTag,
                                                     const UtlString& toTag) const
{
    UtlBoolean isRemoteDialog = FALSE;
    if(callId.compareTo(*this, UtlString::ignoreCase) == 0)
    {
        if((toTag.compareTo(mLocalTag, UtlString::ignoreCase) == 0 ||
            toTag.isNull() || mLocalTag.isNull()) &&
           fromTag.compareTo(mRemoteTag, UtlString::ignoreCase) == 0 ||
           mRemoteTag.isNull()) // If this is remotely initiated fromTag
           // cannot be a null string.  mRemoteTag can be a null string
           // as occurs when a remotely initiated NOTIFY is received 
           // before the SUBSCRIBE response is received.
        {
            isRemoteDialog = TRUE;
        }
    }

    return(isRemoteDialog);
}
示例#3
0
// Activate the escape mechanisms, if the right conditions are present.
// One is the time-out timer, which if it expires, will transfer
// the call back to the user that parked it.
// The other is the escape keycode, which lets the user transfer the call back.
// Neither mechanism is activated if there is no parker URI to transfer back
// to.  Both need appropriate configuration items in the orbits.xml file
// to be activated.
void ParkedCallObject::startEscapeTimer(UtlString& parker,
                                        int timeout,
                                        int keycode)
{
   OsSysLog::add(FAC_PARK, PRI_DEBUG,
                 "ParkedCallObject::startEscapeTimer callId = '%s', "
                 "parker = '%s', timeout = %d, keycode = %d",
                 mOriginalCallId.data(), parker.data(), timeout, keycode);

   // First, check that there is a parker URI.  If not, none of these
   // mechanisms can function.
   if (parker.isNull())
   {
      return;
   }
   // Here, we can insert further validation, such as that the parker URI
   // is local.

   // Save the parker URI.
   mParker = parker;

   if (timeout != OrbitData::NO_TIMEOUT)
   {
      // Set the timeout timer.
      OsTime timeoutOsTime(timeout, 0);
      // Use a periodic timer, so if the transfer generated by one timeout
      // fails, we will try again later.
      mTimeoutTimer.periodicEvery(timeoutOsTime, timeoutOsTime);
   }
   // Remember the keycode for escaping, if any.
   mKeycode = keycode;
   if (mKeycode != OrbitData::NO_KEYCODE)
   {
      // Register the DTMF listener.
      // The "interdigit timeout" time of 1 is just a guess.
      // Enable keyup events, as those are the ones we will act on.
      mpCallManager->enableDtmfEvent(mOriginalCallId.data(), 1,
                                     &mDtmfEvent, false);
   }
}
示例#4
0
/// Retrieve the User PIN check values for a given identity and realm
UtlBoolean CredentialDB::getUserPin (
   const Url& uri,
   const UtlString& realm,
   UtlString& userid,
   UtlString& pintoken,
   UtlString& authType 
                                     ) const 
{
   UtlBoolean found = FALSE;

   UtlString identity;
   uri.getIdentity(identity);

   // Match the row and return the passtoken and authtype
   if ( !identity.isNull() && (m_pFastDB != NULL) )
   {
      // Thread Local Storage
      m_pFastDB->attach();

      dbCursor< CredentialRow > cursor;

      dbQuery query;
      query="np_identity=",identity, \
         "and realm=",realm, \
         "order by np_identity asc, realm asc";

      if ( cursor.select( query ) > 0 )
      {
         do {
            userid = cursor->userid;
            pintoken = cursor->pintoken;
            authType = cursor->authtype;
            found = TRUE;
         } while ( cursor.next() );
      }
      // Commit rows to memory - multiprocess workaround
      m_pFastDB->detach(0);
   }
   return found;
}
示例#5
0
/// Get the caller alias for this combination of caller identity and target domain.
bool CallerAliasDB::getCallerAlias (
   const UtlString& identity, ///< identity of caller in 'user@domain' form (no scheme)
   const UtlString& domain,   /**< domain and optional port for target
                               *  ( 'example.com' or 'example.com:5099' ) */
   UtlString& callerAlias     /// returned alias
                     ) const
{
   /*
    * This first looks in the database for an exact match of identity and domain;
    *   if this match is found, the resulting alias is returned in callerAlias.
    * If no exact match is found, the database is then checked for a row containing
    *   a null (empty string) identity and the domain; this is a domain wildcard entry
    *   and it is returned in callerAlias.
    * If neither match is found, callerAlias is set to the null string.
    */
   callerAlias.remove(0);
   
   if (mpFastDB)
   {
      // Thread Local Storage
      mpFastDB->attach();

      // Search to see if we have a row with this exact combination
      dbQuery exactQuery;
      exactQuery="identity=",identity.data()," and domain=",domain.data();
      dbCursor< CallerAliasRow > exactCursor;
      if (exactCursor.select(exactQuery))
      {
         // found a match 
         callerAlias.append(exactCursor->alias);
      }
        
      // Commit the rows to memory - multiprocess workaround
      mpFastDB->detach(0);
   }

   // Returns true if an alias was found for this caller, false if not
   return ! callerAlias.isNull();
}
示例#6
0
void XCpCall::destroySipConnection(const SipDialog& sSipDialog)
{
   UtlString sSipCallId;
   {
      // check that we really have connection with given sip dialog
      OsLock lock(m_memberMutex);
      if (m_pSipConnection && m_pSipConnection->compareSipDialog(sSipDialog) != SipDialog::DIALOG_MISMATCH)
      {
         // dialog matches
         sSipDialog.getCallId(sSipCallId);
         m_pSipConnection->acquireExclusive();
         delete m_pSipConnection;
         m_pSipConnection = NULL;
      }
   }

   if (!sSipCallId.isNull())
   {
      // we destroyed some connection, notify call stack
      onConnectionRemoved(sSipCallId);
   }
}
示例#7
0
void SipLine::setIdentityAndUrl(Url identity, Url userEnteredUrl)
{
   UtlString identityHost;
   UtlString address;
   int identityPort;

   mIdentity = identity;
   mLineId.remove(0);
   generateLineID(mLineId);
   mUserEnteredUrl = userEnteredUrl;
   //construct a complete url from identity and userEntered Url.
   mCanonicalUrl = mUserEnteredUrl;
   
   mUserEnteredUrl.getHostAddress(address);
   if (address.isNull())
   {     
      mIdentity.getHostAddress(identityHost);
      identityPort = mIdentity.getHostPort();
      mCanonicalUrl.setHostAddress(identityHost);
      mCanonicalUrl.setHostPort(identityPort);
   }
}
示例#8
0
UtlBoolean 
ExtensionDB::getUri (
    const UtlString& extension,
    Url& rUri ) const
{
    UtlBoolean found = FALSE;
    if ( !extension.isNull() && (m_pFastDB != NULL) )
    {
        // Thread Local Storage
        m_pFastDB->attach();

        dbQuery query;

        // Primary Key is the uriExtension's identity
        query="extension=",extension;

        // Search to see if we have a Credential Row
        dbCursor< ExtensionRow > cursor;

        // new style extensions have a domain specifier
        // we can only return true here if we have one unique
        // row, if there are > 1 rows then we have the same extension
        // used in multiple domains
        if ( cursor.select(query) == 1 )
        {
            // should only be row
            do {
                // The serialized vrsion of the uri
                // is compatible with the Uri constructor
                rUri = cursor->uri;
            } while ( cursor.next() );
            found = TRUE;
        }
        // Commit the rows to memory - multiprocess workaround
        m_pFastDB->detach(0);
    }
    return found;
}
示例#9
0
TaoStatus TaoListenerManager::addEventListener(TaoMessage& rMsg)
{
        UtlString terminalName;

        TaoString str(rMsg.getArgList(), TAOMESSAGE_DELIMITER);
        terminalName = str[0];

        if (terminalName.isNull() || 0 == terminalName.compareTo("0.0.0.0"))
        {
                if (mListenerCnt <= 0)
                {
                        terminalName = "127.0.0.1";
                        osPrintf("WARNING - TaoListenerManager::addEventListener: using invalid host, replaced with %s\n", terminalName.data());
                }
                else
                {
                        osPrintf("WARNING - TaoListenerManager::addEventListener: using invalid host %s, listener not added.\n", terminalName.data());
                        return TAO_FAILURE;
                }
        }

        return addEventListener(terminalName.data(), FALSE);
}
    void testManipulators()
    {
       NetAttributeTokenizer a("Basic realm = \"/root/subdir\", ddd=\"no end quote");
       UtlString name;
       UtlString value;

       a.getNextAttribute(name, value);
       CPPUNIT_ASSERT_MESSAGE("no value given", value.isNull());
       CPPUNIT_ASSERT_MESSAGE("first key", name.compareTo("Basic") == 0);

       a.getNextAttribute(name, value);
       CPPUNIT_ASSERT_MESSAGE("escaped value test 1", value.compareTo("/root/subdir") == 0);
       CPPUNIT_ASSERT_MESSAGE("2nd key", name.compareTo("realm") == 0);

       a.getNextAttribute(name, value);
       CPPUNIT_ASSERT_MESSAGE("graceful handle of no end quote", value.compareTo("no end quote") == 0);
       CPPUNIT_ASSERT_MESSAGE("3rd key", name.compareTo("ddd") == 0);

       NetAttributeTokenizer b("ab =\"bunch\\\' \\\" of escaped \\\\\\\' quotes\\\\\"");
       b.getNextAttribute(name, value);
       CPPUNIT_ASSERT_MESSAGE("parade of toothpicks", value.compareTo("bunch\\\' \\\" of escaped \\\\\\\' quotes\\\\") == 0);
       CPPUNIT_ASSERT_MESSAGE("toothpicks's key value", name.compareTo("ab") == 0);
    }
示例#11
0
/// expireAllBindings for this URI as of 1 second before timeNow
void RegistrationDB::expireAllBindings( const Url& uri
                                       ,const UtlString& callid
                                       ,const int& cseq
                                       ,const int& timeNow
                                       ,const UtlString& primary
                                       ,const Int64& update_number
                                       )
{
    UtlString identity;
    uri.getIdentity(identity);
    int expirationTime = timeNow-1;

    if ( !identity.isNull() && ( m_pFastDB != NULL ) )
    {
        SMART_DB_ACCESS;
        dbCursor< RegistrationRow > cursor(dbCursorForUpdate);
        dbQuery query;
        query="np_identity=",identity," and expires>=",expirationTime;

        if (cursor.select(query) > 0)
        {
           do
           {
              cursor->expires = expirationTime;
              cursor->callid  = callid;
              cursor->cseq    = cseq;
              cursor->primary = primary;
              cursor->update_number = update_number;
              cursor.update();
           } while ( cursor.next() );
        }
    }
    else
    {
       OsSysLog::add(FAC_DB, PRI_CRIT, "RegistrationDB::expireAllBindings failed - no DB");
    }
}
示例#12
0
void SipXecsService::setLogPriority(const OsConfigDb& configSettings, // configuration data
                                    const char* servicePrefix, /* the string "_LOG_LEVEL" is
                                                                * appended to this prefix to
                                                                * find the config directive that
                                                                * sets the level */
                                    OsSysLogPriority defaultLevel // default default is "NOTICE"
                                   )
{
    UtlString logLevel;
    UtlString logLevelTag(servicePrefix);
    logLevelTag.append(LogLevelSuffix);

    configSettings.get(logLevelTag, logLevel);

    OsSysLogPriority priority;
    if ( logLevel.isNull() )
    {
        OsSysLog::add(FAC_KERNEL,PRI_WARNING,
                      "SipXecsService::setLogPriority: %s not found, using '%s'",
                      logLevelTag.data(), OsSysLog::priorityName(defaultLevel)
                     );

        priority = defaultLevel;
    }
    else if ( ! OsSysLog::priority(logLevel.data(), priority))
    {
        OsSysLog::add(FAC_KERNEL,PRI_ERR,
                      "SipXecsService::setLogPriority: %s value '%s' is invalid, using '%s'",
                      logLevelTag.data(), logLevel.data(), OsSysLog::priorityName(defaultLevel)
                     );

        priority = defaultLevel;

    }

    OsSysLog::setLoggingPriority(priority);
}
示例#13
0
UtlBoolean SipRefreshManager::getInitialExpiration(const SipMessage& sipRequest, 
                                            int& expirationPeriod)
{
    UtlString method;
    UtlBoolean foundExpiration = FALSE;
    sipRequest.getRequestMethod(&method);

    if(method.compareTo(SIP_REGISTER_METHOD) == 0)
    {
        // Register could have it in the Contact header
        UtlString requestContactValue;
        if(sipRequest.getContactEntry(0 , &requestContactValue))
        {
            // Get the expires parameter for the contact if it exists
            Url contactUri(requestContactValue);
            UtlString contactExpiresParameter;
            if(contactUri.getFieldParameter(SIP_EXPIRES_FIELD, 
                    contactExpiresParameter) &&
               !contactExpiresParameter.isNull())
            {
                foundExpiration = TRUE;

                // Convert to int
                expirationPeriod = atoi(contactExpiresParameter);
            }
        }
    }

    if(!foundExpiration)
    {
        // Not sure if we care if this is a request or response
        foundExpiration = sipRequest.getExpiresField(&expirationPeriod);
    }

    return(foundExpiration);
}
示例#14
0
void
UserLocationDB::removeRows ( const Url& identityUri )
{
    UtlString identityStr;
    identityUri.getIdentity(identityStr);

    if ( !identityStr.isNull() && ( m_pFastDB != NULL ) )
    {
        // Thread Local Storage
        m_pFastDB->attach();

        dbCursor< UserLocationRow > cursor(dbCursorForUpdate);
        dbQuery query;
        query="identity=",identityStr;

        if ( cursor.select( query ) > 0 )
        {
            cursor.removeAllSelected();
        }
        // Commit rows to memory - multiprocess workaround
        m_pFastDB->detach(0);
    }
    return;
}
示例#15
0
UtlBoolean
ExtensionDB::getExtension (
    const Url& uri,
    UtlString& rExtesnion ) const
{
    UtlBoolean found = FALSE;

    UtlString identity;
    uri.getIdentity(identity);

    if ( !identity.isNull() && (m_pFastDB != NULL) )
    {
        // Thread Local Storage
        m_pFastDB->attach();

        dbQuery query;

        // Primary Key is the uriExtension's identity
        query="np_identity=",identity;

        // Search to see if we have a Credential Row
        dbCursor< ExtensionRow > cursor;

        if ( cursor.select(query) > 0 )
        {
            // should only be row
            do {
                rExtesnion = cursor->extension;
            } while ( cursor.next() );
            found = TRUE;
        }
        // Commit the rows to memory - multiprocess workaround
        m_pFastDB->detach(0);
    }
    return found;
}
示例#16
0
文件: main.cpp 项目: astubbs/sipxecs
//
// The main entry point to the sipXpark
//
int main(int argc, char* argv[])
{
   // Block all signals in this the main thread.
   // Any threads created from now on will have all signals masked.
   OsTask::blockSignals();

   // Create a new task to wait for signals.  Only that task
   // will ever see a signal from the outside.
   SignalTask* signalTask = new SignalTask();
   signalTask->start();

    // Configuration Database (used for OsSysLog)
    OsConfigDb configDb;

    UtlString argString;
    for(int argIndex = 1; argIndex < argc; argIndex++)
    {
        osPrintf("arg[%d]: %s\n", argIndex, argv[argIndex]);
        argString = argv[argIndex];
        NameValueTokenizer::frontBackTrim(&argString, "\t ");
        if(argString.compareTo("-v") == 0)
        {
            osPrintf("Version: %s (%s)\n", SIPX_VERSION, SIPX_BUILD);
            return(1);
        } else
        {
           osPrintf("usage: %s [-v]\nwhere:\n -v provides the software version\n",
            argv[0]);
            return(1);
        }
    }

    // Load configuration file file
    OsPath workingDirectory;
    if (OsFileSystem::exists(CONFIG_ETC_DIR))
    {
        workingDirectory = CONFIG_ETC_DIR;
        OsPath path(workingDirectory);
        path.getNativePath(workingDirectory);
    } else
    {
        OsPath path;
        OsFileSystem::getWorkingDirectory(path);
        path.getNativePath(workingDirectory);
    }

    UtlString fileName =  workingDirectory +
      OsPathBase::separator +
      CONFIG_SETTINGS_FILE;

    if (configDb.loadFromFile(fileName) != OS_SUCCESS)
    {
       exit(1);
    }

    // Initialize log file
    initSysLog(&configDb);

    // Read the user agent parameters from the config file.
    int UdpPort;
    if (configDb.get(CONFIG_SETTING_UDP_PORT, UdpPort) != OS_SUCCESS)
        UdpPort = PARK_DEFAULT_UDP_PORT;

    int TcpPort;
    if (configDb.get(CONFIG_SETTING_TCP_PORT, TcpPort) != OS_SUCCESS)
        TcpPort = PARK_DEFAULT_TCP_PORT;

    int RtpBase;
    if (configDb.get(CONFIG_SETTING_RTP_PORT, RtpBase) != OS_SUCCESS)
        RtpBase = DEFAULT_RTP_PORT;

    UtlString bindIp;
    if (configDb.get(CONFIG_SETTING_BIND_IP, bindIp) != OS_SUCCESS ||
            !OsSocket::isIp4Address(bindIp))
        bindIp = PARK_DEFAULT_BIND_IP;

    int MaxSessions;
    if (configDb.get(CONFIG_SETTING_MAX_SESSIONS, MaxSessions) != OS_SUCCESS)
    {
        MaxSessions = DEFAULT_MAX_SESSIONS;
    }

    UtlBoolean OneButtonBLF =
       configDb.getBoolean(CONFIG_SETTING_ONE_BUTTON_BLF, DEFAULT_ONE_BUTTON_BLF);

    UtlString   domain;
    UtlString   realm;
    UtlString   user;

    SipLine*    line = NULL;
    SipLineMgr* lineMgr = NULL;

    OsConfigDb  domainConfiguration;
    OsPath      domainConfigPath = SipXecsService::domainConfigPath();

    if (OS_SUCCESS == domainConfiguration.loadFromFile(domainConfigPath.data()))
    {
       domainConfiguration.get(SipXecsService::DomainDbKey::SIP_DOMAIN_NAME, domain);
       domainConfiguration.get(SipXecsService::DomainDbKey::SIP_REALM, realm);

       if (!domain.isNull() && !realm.isNull())
       {
          CredentialDB* credentialDb;
          if ((credentialDb = CredentialDB::getInstance()))
          {
             Url identity;

             identity.setUserId(PARK_SERVER_ID_TOKEN);
             identity.setHostAddress(domain);

             UtlString ha1_authenticator;
             UtlString authtype;

             if (credentialDb->getCredential(identity, realm, user, ha1_authenticator, authtype))
             {
                if ((line = new SipLine( identity // user entered url
                                        ,identity // identity url
                                        ,user     // user
                                        ,TRUE     // visible
                                        ,SipLine::LINE_STATE_PROVISIONED
                                        ,TRUE     // auto enable
                                        ,FALSE    // use call handling
                                        )))
                {
                   if ((lineMgr = new SipLineMgr()))
                   {
                      if (lineMgr->addLine(*line))
                      {
                         if (lineMgr->addCredentialForLine( identity, realm, user, ha1_authenticator
                                                           ,HTTP_DIGEST_AUTHENTICATION
                                                           )
                             )
                         {
                            OsSysLog::add(LOG_FACILITY, PRI_INFO,
                                          "Added identity '%s': user='******' realm='%s'"
                                          ,identity.toString().data(), user.data(), realm.data()
                                          );
                         }
                         else
                         {
                            OsSysLog::add(LOG_FACILITY, PRI_ERR,
                                          "Error adding identity '%s': user='******' realm='%s'\n"
                                          "  escape and timeout from park may not work.",
                                          identity.toString().data(), user.data(), realm.data()
                                          );
                         }

                         lineMgr->setDefaultOutboundLine(identity);
                      }     // end addLine
                      else
                      {
                         OsSysLog::add(LOG_FACILITY, PRI_ERR,
                                       "addLine failed: "
                                       "  escape and timeout from park may not work."
                                       );
                      }
                   }
                   else
                   {
                      OsSysLog::add(LOG_FACILITY, PRI_ERR,
                                    "Constructing SipLineMgr failed:  "
                                    "  escape and timeout from park may not work."
                                    );
                   }
                }   // end new SipLine
                else
                {
                   OsSysLog::add(LOG_FACILITY, PRI_ERR,
                                 "Constructing SipLine failed:  "
                                 "  escape and timeout from park may not work."
                                 );
                }
             }  // end getCredential
             else
             {
                OsSysLog::add(LOG_FACILITY, PRI_ERR,
                              "No credential found for '%s@%s' in realm '%s'"
                              "; transfer functions will not work",
                              PARK_SERVER_ID_TOKEN, domain.data(), realm.data()
                              );
             }

             credentialDb->releaseInstance();
          }   // end credentialDB
          else
          {
             OsSysLog::add(LOG_FACILITY, PRI_ERR,
                           "Failed to open credentials database"
                           "; transfer functions will not work"
                           );
          }
       }    // end have domain and realm
       else
       {
          OsSysLog::add(LOG_FACILITY, PRI_ERR,
                        "Domain or Realm not configured:"
                        "\n  '%s' : '%s'\n  '%s' : '%s'"
                        "  transfer functions will not work.",
                        SipXecsService::DomainDbKey::SIP_DOMAIN_NAME, domain.data(),
                        SipXecsService::DomainDbKey::SIP_REALM, realm.data()
                        );
       }
    }       // end found domain config
    else
    {
       OsSysLog::add(LOG_FACILITY, PRI_ERR,
                     "main: failed to load domain configuration from '%s'",
                     domainConfigPath.data()
                     );
    }

    // Read Park Server parameters from the config file.
    int Lifetime, BlindXferWait, KeepAliveTime, ConsXferWait;
    if (configDb.get(CONFIG_SETTING_LIFETIME, Lifetime) != OS_SUCCESS)
    {
       Lifetime = DEFAULT_LIFETIME;
    }
    if (configDb.get(CONFIG_SETTING_BLIND_WAIT, BlindXferWait) != OS_SUCCESS)
    {
       BlindXferWait = DEFAULT_BLIND_WAIT;
    }
    if (configDb.get(CONFIG_SETTING_KEEPALIVE_TIME, KeepAliveTime) != OS_SUCCESS)
    {
       KeepAliveTime = DEFAULT_KEEPALIVE_TIME;
    }
    // This is not configurable, as consultative transfers should
    // succeed or fail immediately.
    ConsXferWait = CONS_XFER_WAIT;

    // Bind the SIP user agent to a port and start it up
    SipUserAgent* userAgent = new SipUserAgent(TcpPort,
                                               UdpPort,
                                               TcpPort+1,
                                               NULL, // publicAddress
                                               user.isNull() ? NULL : user.data(), // default user
                                               bindIp,
                                               domain.isNull() ? NULL : domain.data(), // outbound proxy
                                               NULL, // sipDirectoryServers (deprecated)
                                               NULL, // sipRegistryServers (deprecated)
                                               NULL, // authenticationScheme
                                               NULL, // authenicateRealm
                                               NULL, // authenticateDb
                                               NULL, // authorizeUserIds (deprecated)
                                               NULL, // authorizePasswords (deprecated)
                                               lineMgr
                                               );
    userAgent->setUserAgentHeaderProperty("sipXecs/park");
    userAgent->start();

    if (!userAgent->isOk())
    {
       OsSysLog::add(LOG_FACILITY, PRI_EMERG, "SipUserAgent failed to initialize, requesting shutdown");
       gShutdownFlag = TRUE;
    }

    // Read the list of codecs from the configuration file.
    SdpCodecFactory codecFactory;
    initCodecs(&codecFactory, &configDb);

    // Initialize and start up the media subsystem
    mpStartUp(MP_SAMPLE_RATE, MP_SAMPLES_PER_FRAME, 6 * MaxSessions, &configDb);
    MpMediaTask::getMediaTask(MaxSessions);

#ifdef INCLUDE_RTCP
    CRTCManager::getRTCPControl();
#endif //INCLUDE_RTCP

    mpStartTasks();

    // Instantiate the call processing subsystem
    UtlString localAddress;
    int localPort ;
    userAgent->getLocalAddress(&localAddress, &localPort) ;
    if (localAddress.isNull())
        OsSocket::getHostIp(&localAddress);

    // Construct an address to be used in outgoing requests (primarily
    // INVITEs stimulated by REFERs).
    UtlString outgoingAddress;
    {
       char buffer[100];
       sprintf(buffer, "sip:sipXpark@%s:%d", localAddress.data(),
               portIsValid(UdpPort) ? UdpPort : TcpPort);
       outgoingAddress = buffer;
    }
    CallManager callManager(FALSE,
                           NULL,
                           TRUE,                              // early media in 180 ringing
                           &codecFactory,
                           RtpBase,                           // rtp start
                           RtpBase + (2 * MaxSessions),       // rtp end
                           localAddress,
                           localAddress,
                           userAgent,
                           0,                                 // sipSessionReinviteTimer
                           NULL,                              // mgcpStackTask
                           outgoingAddress,                   // defaultCallExtension
                           Connection::RING,                  // availableBehavior
                           NULL,                              // unconditionalForwardUrl
                           -1,                                // forwardOnNoAnswerSeconds
                           NULL,                              // forwardOnNoAnswerUrl
                           Connection::BUSY,                  // busyBehavior
                           NULL,                              // sipForwardOnBusyUrl
                           NULL,                              // speedNums
                           CallManager::SIP_CALL,             // phonesetOutgoingCallProtocol
                           4,                                 // numDialPlanDigits
                           CallManager::NEAR_END_HOLD,        // holdType
                           5000,                              // offeringDelay
                           "",                                // pLocal
                           CP_MAXIMUM_RINGING_EXPIRE_SECONDS, // inviteExpiresSeconds
                           QOS_LAYER3_LOW_DELAY_IP_TOS,       // expeditedIpTos
                           MaxSessions,                       // maxCalls
                           sipXmediaFactoryFactory(NULL));    // CpMediaInterfaceFactory



    // Create a listener (application) to deal with call
    // processing events (e.g. incoming call and hang ups)
    OrbitListener listener(&callManager, Lifetime, BlindXferWait, KeepAliveTime, ConsXferWait);

    callManager.addTaoListener(&listener);
    listener.start();

    // Create the SIP Subscribe Server
    SipPersistentSubscriptionMgr
       subscriptionMgr(SUBSCRIPTION_COMPONENT_PARK,
                       domain,
                       "subscription"); // Component for holding the subscription data
    SipSubscribeServerEventHandler policyHolder; // Component for granting the subscription rights
    SipPublishContentMgr publisher; // Component for publishing the event contents

    SipSubscribeServer subscribeServer(*userAgent, publisher,
                                       subscriptionMgr, policyHolder);
    subscribeServer.enableEventType(DIALOG_EVENT_TYPE);
    subscribeServer.start();

    // Create the DialogEventPublisher.
    // Use the sipX domain as the hostport of resource-IDs of the
    // published events, as that will be the request-URIs of SUBSCRIBEs.
    DialogEventPublisher dialogEvents(&callManager, &publisher, domain, PORT_NONE, OneButtonBLF);
    callManager.addTaoListener(&dialogEvents);
    dialogEvents.start();

    // Start up the call processing system
    callManager.start();

    // Loop forever until signaled to shut down

    int numTwoSecIntervals = 0;
    int CleanLoopWaitTimeSecs = 10;

    while (!gShutdownFlag)
    {
       OsTask::delay(2000);

       if (2*numTwoSecIntervals >= CleanLoopWaitTimeSecs)
       {
           numTwoSecIntervals = 0;
           if (OsSysLog::willLog(FAC_PARK, PRI_DEBUG))
           {
               OsSysLog::add(LOG_FACILITY, PRI_DEBUG,
                             "park main "
                             "logging call status"
                             );
               callManager.printCalls(0) ;
               listener.dumpCallsAndTransfers();
           }
       }
       else
       {
           numTwoSecIntervals += 1;
       }

    }

    // Flush the log file
    OsSysLog::flush();

    // Say goodnight Gracie...
    return 0;
}
示例#17
0
文件: main.cpp 项目: astubbs/sipxecs
// Initialize the OsSysLog
void initSysLog(OsConfigDb* pConfig)
{
   UtlString logLevel;               // Controls Log Verbosity
   UtlString consoleLogging;         // Enable console logging by default?
   UtlString fileTarget;             // Path to store log file.
   UtlBoolean bSpecifiedDirError ;   // Set if the specified log dir does not
                                    // exist

   OsSysLog::initialize(0, "sipxpark");
   OsSysLog::add(FAC_SIP, PRI_INFO, ">>>>>>>>>>>>>>>> Starting - version %s build %s",
                 SIPX_VERSION, SIPX_BUILD
                 );

   //
   // Get/Apply Log Filename
   //
   fileTarget.remove(0);
   if ((pConfig->get(CONFIG_SETTING_LOG_DIR, fileTarget) != OS_SUCCESS) ||
      fileTarget.isNull() || !OsFileSystem::exists(fileTarget))
   {
      bSpecifiedDirError = !fileTarget.isNull();

      // If the log file directory exists use that, otherwise place the log
      // in the current directory
      OsPath workingDirectory;
      if (OsFileSystem::exists(CONFIG_LOG_DIR))
      {
         fileTarget = CONFIG_LOG_DIR;
         OsPath path(fileTarget);
         path.getNativePath(workingDirectory);

         osPrintf("%s : %s\n", CONFIG_SETTING_LOG_DIR, workingDirectory.data());
         OsSysLog::add(LOG_FACILITY, PRI_INFO, "%s : %s", CONFIG_SETTING_LOG_DIR, workingDirectory.data());
      }
      else
      {
         OsPath path;
         OsFileSystem::getWorkingDirectory(path);
         path.getNativePath(workingDirectory);

         osPrintf("%s : %s\n", CONFIG_SETTING_LOG_DIR, workingDirectory.data());
         OsSysLog::add(LOG_FACILITY, PRI_INFO, "%s : %s", CONFIG_SETTING_LOG_DIR, workingDirectory.data());
      }

      fileTarget = workingDirectory +
         OsPathBase::separator +
         CONFIG_LOG_FILE;
   }
   else
   {
      bSpecifiedDirError = false;
      osPrintf("%s : %s\n", CONFIG_SETTING_LOG_DIR, fileTarget.data());
      OsSysLog::add(LOG_FACILITY, PRI_INFO, "%s : %s", CONFIG_SETTING_LOG_DIR, fileTarget.data());

      fileTarget = fileTarget +
         OsPathBase::separator +
         CONFIG_LOG_FILE;
   }
   OsSysLog::setOutputFile(0, fileTarget);


   //
   // Get/Apply Log Level
   //
   SipXecsService::setLogPriority(*pConfig, CONFIG_SETTING_PREFIX, PRI_ERR);
   OsSysLog::setLoggingPriorityForFacility(FAC_SIP_INCOMING_PARSED, PRI_ERR);

   //
   // Get/Apply console logging
   //
   UtlBoolean bConsoleLoggingEnabled = false;
   if ((pConfig->get(CONFIG_SETTING_LOG_CONSOLE, consoleLogging) == OS_SUCCESS))
   {
      consoleLogging.toUpper();
      if (consoleLogging == "ENABLE")
      {
         OsSysLog::enableConsoleOutput(true);
         bConsoleLoggingEnabled = true;
      }
   }

   osPrintf("%s : %s\n", CONFIG_SETTING_LOG_CONSOLE, bConsoleLoggingEnabled ? "ENABLE" : "DISABLE") ;
   OsSysLog::add(LOG_FACILITY, PRI_INFO, "%s : %s", CONFIG_SETTING_LOG_CONSOLE, bConsoleLoggingEnabled ? "ENABLE" : "DISABLE") ;

   if (bSpecifiedDirError)
   {
      OsSysLog::add(FAC_LOG, PRI_CRIT, "Cannot access %s directory; please check configuration.", CONFIG_SETTING_LOG_DIR);
   }
}
示例#18
0
//! Generate the HttpBody for the current state of the resource list.
HttpBody* ResourceList::generateRlmiBody(UtlBoolean consolidated,
                                         UtlBoolean fullRlmi,
                                         UtlSList& listToSend)
{
   if (Os::Logger::instance().willLog(FAC_RLS, PRI_DEBUG))
   {
      UtlString l;

      UtlSListIterator resourcesItor(listToSend);
      ResourceReference* resource;
      while ((resource = dynamic_cast <ResourceReference*> (resourcesItor())))
      {
         l.append(*resource->getUri());
         l.append(",");
      }
      if (!l.isNull())
      {
         l.remove(l.length() - 1);
      }

      Os::Logger::instance().log(FAC_RLS, PRI_DEBUG,
                    "ResourceList::generateRlmiBody cons=%d URI='%s' full=%d listToSend='%s'",
                    consolidated,
                    (consolidated ? mResourceListNameCons.data() : mResourceListName.data()),
                    fullRlmi,
                    l.data());
   }

   // Construct the multipart body.
   // We add the <...> here, as they are used in all the contexts where
   // rlmiBodyPartCid appears.
   UtlString rlmiBodyPartCid;
   rlmiBodyPartCid += "<rlmi@";
   rlmiBodyPartCid += getResourceListServer()->getDomainName();
   rlmiBodyPartCid += ">";

   UtlString content_type(CONTENT_TYPE_MULTIPART_RELATED
                          ";type=\"" RLMI_CONTENT_TYPE "\""
                          ";start=\"");
   content_type += rlmiBodyPartCid;
   content_type += "\"";
   HttpBody* body = new HttpBodyMultipart(content_type);

   // This is the Resource List Meta-Information, XML describing the resources
   // and their instances.  It is the main part of the NOTIFY body.
   UtlString rlmi;

   // Generate the initial part of the RLMI.
   rlmi += "<?xml version=\"1.0\"?>\r\n";
   rlmi += "<list xmlns=\"" RLMI_XMLNS "\" uri=\"";
   XmlEscape(rlmi,
             consolidated ? mResourceListNameCons : mResourceListName);
   // Placeholder for version from SIP stack.
   rlmi += "\" version=\"" VERSION_PLACEHOLDER "\" ";

   // Generate either the full or the partial RLMI.
   if (fullRlmi)
   {
      rlmi += "fullState=\"true\">\r\n";
   }
   else
   {
      rlmi += "fullState=\"false\">\r\n";
   }

   // If we implemented names for resource lists, <name> elements would be added here.

   // Iterate through the resources.
   UtlSListIterator resourcesItor(listToSend);
   ResourceReference* resource;
   while ((resource = dynamic_cast <ResourceReference*> (resourcesItor())))
   {
      // Add the content for the resource.
      resource->generateBody(rlmi, *body, consolidated);
   }

   // Generate the postamble for the resource list.
   rlmi += "</list>\r\n";

   // Construct the RLMI body part.
   HttpBody rlmi_body(rlmi.data(), rlmi.length(), RLMI_CONTENT_TYPE);
   UtlDList rlmi_body_parameters;
   rlmi_body_parameters.append(new NameValuePair(HTTP_CONTENT_ID_FIELD,
                                                 rlmiBodyPartCid));

   // Attach the RLMI.
   body->appendBodyPart(rlmi_body, rlmi_body_parameters);

   // Clean up the parameter list.
   rlmi_body_parameters.destroyAll();

   return body;
}
示例#19
0
OsStatus
DialByNameDB::load() const
{
    // Critical Section here
    OsLock lock( sLockMutex );
    OsStatus result = OS_SUCCESS;

    if ( m_pFastDB != NULL ) 
    {
        // Clean out the existing DB rows before loading
        // a new set from persistent storage
        removeAllRows ();

        // Query all Identities with 'AutoAttendant' permission set
        PermissionDB * pPermissionDB = PermissionDB::getInstance();
        ResultSet permissionsResultSet;
        pPermissionDB->getIdentities ( "AutoAttendant", permissionsResultSet );

        CredentialDB * pCredentialDB = CredentialDB::getInstance();
        ResultSet credentialsResultSet;

        UtlString identity, permission;
        int numAutoAttendees = permissionsResultSet.getSize();
        for (int index = 0; index < numAutoAttendees; index++)
        {
            // get the next identity
            UtlString identityKey("identity");
            UtlHashMap record;
            permissionsResultSet.getIndex( index, record );
            UtlString identity = *((UtlString*)record.findValue(&identityKey));

            Url identityUrl (identity);
            pCredentialDB->
                getAllCredentials (
                    identityUrl,
                    credentialsResultSet );

            // we should only have one credential! we're 
            // only interested in the uri column's display name
            if ( credentialsResultSet.getSize() == 1)
            {
                UtlString uriKey("uri");
                UtlHashMap record;
                credentialsResultSet.getIndex( 0, record );
                UtlString uri = *((UtlString*)record.findValue(&uriKey));

                // must have a display name present before inserting a row
                // @TODO convert to url and get display name
                UtlHashMap nvPairs;
                if (!uri.isNull())
                {
                    // Null Element value create a special 
                    // char string we have key and value so insert
                    UtlString* contactValue = 
                        new UtlString( uri ); 

                    // Memory Leak fixes, make shallow copies of static keys
                    UtlString* contactKey = 
                        new UtlString( gNp_contactKey );

                    nvPairs.insertKeyAndValue ( 
                        contactKey, contactValue );
                }
                // Insert the item row into the IMDB
                insertRow ( nvPairs );
            }
        }

        // Reset the changed flags after a successful load
        SIPDBManager::getInstance()->
            setDatabaseChangedFlag("credential", FALSE);
        SIPDBManager::getInstance()->
            setDatabaseChangedFlag("permission", FALSE);
    } else
    {
        result = OS_FAILED;
    }
    return result;
}
示例#20
0
UtlBoolean SipRegistrar::handleMessage( OsMsg& eventMessage )
{
    UtlBoolean handled = FALSE;

    int msgType = eventMessage.getMsgType();
    int msgSubType = eventMessage.getMsgSubType();

    if (   (msgType == OsMsg::PHONE_APP)
        && (msgSubType == SipMessage::NET_SIP_MESSAGE)
        )
    {
        Os::Logger::instance().log(FAC_SIP, PRI_DEBUG, "SipRegistrar::handleMessage()"
                      " Start processing SIP message") ;

        const SipMessage* message =
           ((SipMessageEvent&)eventMessage).getMessage();
        UtlString callId;
        if ( message )
        {
            message->getCallIdField(&callId);
            UtlString method;
            message->getRequestMethod(&method);

            if ( !message->isResponse() ) // is a request ?
            {
                if ( method.compareTo(SIP_REGISTER_METHOD) == 0 )
                {
                    //send to Register Thread
                    sendToRegistrarServer(eventMessage);
                }
                else if ( method.compareTo(SIP_OPTIONS_METHOD) == 0 )
                {
                    UtlString requestUri;
                    message->getRequestUri(&requestUri);

                    // Check if the OPTIONS request URI is addressed to a user or
                    // to the domain.
                    if (!requestUri.contains("@"))
                    {
                        UtlString contentEncoding;
                        message->getContentEncodingField(&contentEncoding);

                        UtlString disallowedExtensions;

                        int extensionIndex = 0;
                        UtlString extension;

                        disallowedExtensions.remove(0);
                        while(message->getRequireExtension(extensionIndex, &extension))
                        {
                            if(!(mSipUserAgent->isExtensionAllowed(extension.data())) )
                            {
                                if(!disallowedExtensions.isNull())
                                {
                                    disallowedExtensions.append(SIP_MULTIFIELD_SEPARATOR);
                                    disallowedExtensions.append(SIP_SINGLE_SPACE);
                                }
                                disallowedExtensions.append(extension.data());
                            }
                            extensionIndex++;
                        }

                        //delete leading and trailing white spaces
                        disallowedExtensions = disallowedExtensions.strip(UtlString::both);

                        SipMessage response;

                        // Check if the extensions are supported
                        if(!disallowedExtensions.isNull() )
                        {
                           // error response - bad extension
                           response.setRequestBadExtension(message,
                                                           disallowedExtensions);
                        }
                        // Check if the encoding is supported
                        // i.e. no encoding
                        else if(!contentEncoding.isNull())
                        {
                           // error response - content encoding
                           response.setRequestBadContentEncoding(message,"");
                        }
                        else
                        {
                            // Send an OK, the allowed field will get added to all final responses.
                            // Options 200 response
                            response.setResponseData(message,
                                                     SIP_OK_CODE,
                                                     SIP_OK_TEXT);
                        }

                        mSipUserAgent->send(response);
                    }
                    else
                    {
                        //OPTIONS is addressed to a user, send to redirect thread
                        sendToRedirectServer(eventMessage);
                    }
                }
                else
                {
                    //send to redirect thread
                    sendToRedirectServer(eventMessage);
                }
            }
            else
            {
               // responses are ignored.
            }
        }
        else
        {
           Os::Logger::instance().log(FAC_SIP, PRI_DEBUG,
                         "SipRegistrar::handleMessage no message."
                         ) ;
        }

        handled = TRUE;
    }
    else if ( OsMsg::OS_SHUTDOWN == msgType )
    {
       Os::Logger::instance().log(FAC_SIP, PRI_DEBUG,
                     "SipRegistrar::handleMessage shutting down all tasks");

       // Do an orderly shutdown of all the various threads.


       if ( mSipUserAgent )
       {
          Os::Logger::instance().log(FAC_SIP, PRI_DEBUG,
                        "SipRegistrar::handleMessage shutting down SipUserAgent");
          mSipUserAgent->shutdown();
          delete mSipUserAgent ;
          mSipUserAgent = NULL ;
       }


       if ( mRegistrarPersist )
       {
          Os::Logger::instance().log(FAC_SIP, PRI_DEBUG,
                        "SipRegistrar::handleMessage shutting down RegistrarPersist");
          mRegistrarPersist->requestShutdown();
          delete mRegistrarPersist;
          mRegistrarPersist = NULL;
       }

       if ( mRedirectServer )
       {
          Os::Logger::instance().log(FAC_SIP, PRI_DEBUG,
                        "SipRegistrar::handleMessage shutting down RedirectServer");
          mRedirectServer->requestShutdown();
          delete mRedirectServer;
          mRedirectServer = NULL;
          mRedirectMsgQ = NULL;
       }

       if ( mRegistrarServer )
       {
          Os::Logger::instance().log(FAC_SIP, PRI_DEBUG,
                        "SipRegistrar::handleMessage shutting down RegistrarServer");
          mRegistrarServer->requestShutdown();
          delete mRegistrarServer;
          mRegistrarServer = NULL;
          mRegistrarMsgQ = NULL;
       }

       if ( mRegisterEventServer )
       {
          Os::Logger::instance().log(FAC_SIP, PRI_DEBUG,
                        "SipRegistrar::handleMessage shutting down RegisterEventServer");
          delete mRegisterEventServer;
          mRegisterEventServer = NULL;
       }

       OsTask::requestShutdown(); // tell OsServerTask::run to exit
       handled = TRUE;
    }
    else
    {
       Os::Logger::instance().log(FAC_SIP, PRI_DEBUG,
                     "SipRegistrar::handleMessage unhandled type %d/%d",
                     msgType, msgSubType
                     ) ;
    }

    return handled;
}
示例#21
0
///////////////////////////PUBLIC///////////////////////////////////
UtlBoolean
SubscribeServerThread::initialize (
    SipUserAgent* sipUserAgent,
    int defaultSubscribePeriod,
    const UtlString& minExpiresTime,
    const UtlString& defaultDomain,
    const UtlBoolean& useCredentialDB,
    const UtlString& realm,
    PluginXmlParser* pluginTable)
{
    if ( !mIsStarted )
    {
        //start the thread
        start();
    }

    if ( !minExpiresTime.isNull() )
    {
        mMinExpiresTimeStr.append(minExpiresTime);
        mMinExpiresTimeint = atoi(minExpiresTime.data());
    }

    mDefaultSubscribePeriod = defaultSubscribePeriod;
    if ( mMinExpiresTimeint > mDefaultSubscribePeriod )
    {
       OsSysLog::add(FAC_SIP, PRI_ERR,
                     "SubscribeServerThread::initialize - minimum expiration time (%d)"
                     " > default/maximum expiration time (%d); reset to equal",
                     mMinExpiresTimeint,
                     mDefaultSubscribePeriod
          );
       mMinExpiresTimeint = mDefaultSubscribePeriod;
    }

    if ( !defaultDomain.isNull() )
    {
        mDefaultDomain.remove(0);
        mDefaultDomain.append( defaultDomain );
        Url defaultDomainUrl( mDefaultDomain );
        mDefaultDomainPort = defaultDomainUrl.getHostPort();

        // the isValidDomain compares the server's domain to
        // that in the incoming URI, sometimes the incoming
        // URI is a dotted IP address.
        UtlString ipOrFQDNHost;

        defaultDomainUrl.getHostAddress(ipOrFQDNHost);

        // sometimes the request URI will contain
        // an IP Address and at others it contains a FQDN
        if ( OsSocket::isIp4Address( ipOrFQDNHost.data() ) )
        {
            mDefaultDomainHostIP = ipOrFQDNHost;
            OsSocket::getDomainName( mDefaultDomainHostFQDN );
        } else
        {
            mDefaultDomainHostFQDN = ipOrFQDNHost;
            OsSocket::getHostIp( &mDefaultDomainHostIP );
        }
    }

    if ( !realm.isNull() )
    {
        mRealm.remove(0);
        mRealm.append(realm);
    }

    mIsCredentialDB = useCredentialDB;

    //get sip user agent
    if ( sipUserAgent )
    {
        mpSipUserAgent = sipUserAgent;
    } else
    {
        mpSipUserAgent = NULL;
        return FALSE;
    }

    //get Plugin table
    if ( pluginTable )
    {
        mPluginTable = pluginTable;
    } else
    {
        return FALSE;
    }
    return TRUE;
}
示例#22
0
int SipUdpServer::run(void* runArg)
{
    int cseq = 1;
    if(mSipUserAgent)
    {
        UtlString contact;
        mSipUserAgent->getContactUri(&contact);

        // Add a tag to the contact and build the from field
        UtlString from(contact);
        int tagRand1 = rand();
        int tagRand2 = rand();
        char fromTag[80];
        sprintf(fromTag, ";tag=%d%d", tagRand1, tagRand2);
        from.append(fromTag);

        UtlString rawAddress;
        int port;
        Url pingUrl(mNatPingUrl);

        // Create a cannonized version of the ping URL in case
        // it does not specify "sip:", etc.
        UtlString cannonizedPingUrl = pingUrl.toString();

        // Get the address and port in the png URL so that
        // we can look up the DNS stuff if needed
        port = pingUrl.getHostPort();
        pingUrl.getHostAddress(rawAddress);

        // Resolve the raw address from a DNS SRV, A record
        // to an IP address
        server_t* dnsSrvRecords =
            SipSrvLookup::servers(rawAddress.data(),
                                  "sip",
                                  OsSocket::UDP,
                                  port);

        // Do a DNS SRV or A record lookup
        // If we started with an IP address, we will still get an IP
        // address in the result
        UtlString address;
        if(dnsSrvRecords[0].isValidServerT())
        {
            // Get the highest priority address and port from the
            // list with randomization of those according to the
            // weights.
            // Note: we are not doing any failover here as that is
            // a little tricky with the NAT stuff.  We cannot change
            // addresses with every transaction as we may get different
            // ports and addresses every time we send a ping.  For now
            // we do one DNS SRV lookup at the begining of time and
            // stick to that result.
            dnsSrvRecords[0].getIpAddressFromServerT(address);
            port = dnsSrvRecords[0].getPortFromServerT();

            // If the ping URL or DNS SRV did not specify a port
            // bind it to the default port.
            if (!portIsValid(port))
            {
               port = SIP_PORT;
            }
        }

        // Did not get a valid response from the DNS lookup
        else
        {
            // Configured with a bad DNS name that did not resolve.
            // Or the DNS server did not respond.
            if(!rawAddress.isNull())
            {
                OsSysLog::add(FAC_SIP, PRI_INFO,
                    "SipUdpServer::run DNS lookup failed for ping host: %s in URI: %s",
                    rawAddress.data(), mNatPingUrl.data());
            }
            // Else no ping address, this means we are not supposed to
            // do a ping
        }
        // Free the list of server addresses.
        delete[] dnsSrvRecords;

        // Get the address to be used in the callId scoping
        int dummyPort;
        UtlString callId;
        
        if (mSipUserAgent)
        {
            mSipUserAgent->getViaInfo(OsSocket::UDP, callId, dummyPort);
        }

        // Make up a call Id
        long epochTime = OsDateTime::getSecsSinceEpoch();
        int randNum = rand();
        char callIdPrefix[80];
        sprintf(callIdPrefix, "%ld%d-ping@", epochTime, randNum);
        callId.insert(0,callIdPrefix);

        while(mNatPingFrequencySeconds > 0 &&
            !mNatPingUrl.isNull() &&
            !mNatPingMethod.isNull() &&
            !address.isNull())
        {
            // Send a no-op SIP message to the
            // server to keep a port open through a NAT
            // based firewall
            SipMessage pingMessage;
            pingMessage.setRequestData(mNatPingMethod, cannonizedPingUrl.data(),
                from.data(), mNatPingUrl.data(), callId, cseq, contact.data());

            // Get the UDP via info from the SipUserAgent
            UtlString viaAddress;
            int viaPort;
            
            if (mSipUserAgent)
            {
                mSipUserAgent->getViaInfo(OsSocket::UDP, viaAddress, viaPort);
            }
            pingMessage.addVia(viaAddress.data(), viaPort, SIP_TRANSPORT_UDP);

            // Mark the via so the receiver knows we support and want the
            // received port to be set
            pingMessage.setLastViaTag("", "rport");
#           ifdef TEST_PRINT            
            osPrintf("Sending ping to %s %d, From: %s\n",
                address.data(), port, contact.data());
#           endif
            
            // Send from the same UDP port that we receive from
            if (mSipUserAgent)
            {
                mSipUserAgent->sendSymmetricUdp(pingMessage, address.data(), port);
            }

            cseq++;

            // Wait until it is time to send another ping
            delay(mNatPingFrequencySeconds * 1000);
        }
    }

    return(mNatPingFrequencySeconds);
}
示例#23
0
// Add to the HttpBody the current state of the resource.
void ResourceCached::generateBody(UtlString& rlmi,
                                  HttpBody& body,
                                  UtlBoolean consolidated,
                                  const UtlString& nameXml,
                                  const UtlString& displayName) const
{
   // Generate the preamble for the resource.
   rlmi += "  <resource uri=\"";
   XmlEscape(rlmi, *(static_cast <const UtlString*> (this)));
   rlmi += "\">\r\n";
   if (!nameXml.isNull())
   {
      rlmi += "    ";
      rlmi += nameXml;
   }

   if (consolidated)
   {
      // If consolidating resource instances, generate the XML for the
      // unified resource instance.
      rlmi += "    <instance id=\"consolidated\" state=\"active\"";

      UtlString contentBodyPartCid;
      // Use the count of parts in 'body' to generate a unique identifier for
      // each part.
      contentBodyPartCid.appendNumber(body.getMultipartCount());
      contentBodyPartCid += "@";
      contentBodyPartCid += getResourceListServer()->getDomainName();

      rlmi += " cid=\"";
      rlmi += contentBodyPartCid;
      rlmi += "\"";

      // Now add the <...> and use it in the header.
      contentBodyPartCid.prepend("<");
      contentBodyPartCid.append(">");

      // Create a single HttpBody to contain the unified dialog event.
      UtlString dialog_event;

      // XML declaration is optional, but Broadworks uses it.
      dialog_event += "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n";
      dialog_event += BEGIN_DIALOG_INFO;
      dialog_event += VERSION_EQUAL;
      dialog_event += "\"";
      // The consolidated dialog events need to have persistent
      // version numbers, as they all have the same instance id.
      // So we use a global version number in the ResourceListSet.
      dialog_event.appendNumber(getResourceListSet()->getVersion());
      dialog_event += "\"";
      dialog_event += STATE_EQUAL;
      dialog_event += "\"full\"";
      dialog_event += ENTITY_EQUAL;
      dialog_event += "\"";
      dialog_event += *(static_cast <const UtlString*> (this));
      dialog_event += "\">\r\n";
      // Save the length of dialog_event, so we can tell later if
      // any <dialog>s have been added to it.
      unsigned int preamble_length = dialog_event.length();

      // Call the ContactSet to generate the consolidated dialog event body.
      if (mContactSetP)
      {
         mContactSetP->generateBody(dialog_event, body, consolidated,
                                    displayName);
      }

      // If no <dialog>s have been added, we have to add a dummy
      // <dialog> to carry the display name.
      if (dialog_event.length() == preamble_length)
      {
         dialog_event +=
            "<dialog id=\";\"><state>terminated</state><local><identity display=\"";
         XmlEscape(dialog_event, displayName);
         dialog_event += "\">";
         XmlEscape(dialog_event, *(static_cast <const UtlString*> (this)));
         dialog_event += "</identity></local></dialog>\r\n";
      }

      dialog_event += END_DIALOG_INFO;

      // Insert the consolidated dialog event body into the multiplart body.
      HttpBody content_body(dialog_event.data(),
                            dialog_event.length(),
                            DIALOG_EVENT_CONTENT_TYPE);
      UtlDList content_body_parameters;
      content_body_parameters.append(
         new NameValuePair(HTTP_CONTENT_ID_FIELD,
                           contentBodyPartCid));
      body.appendBodyPart(content_body, content_body_parameters);
      content_body_parameters.destroyAll();

      // Finish the <instance> element.
      rlmi += "/>\r\n";
   }
   else
   {
      // Call the ContactSet to do the work.
      if (mContactSetP)
      {
         mContactSetP->generateBody(rlmi, body, consolidated, displayName);
      }
   }   
   
// Generate the postamble for the resource.
   rlmi += "  </resource>\r\n";
}
示例#24
0
UtlBoolean CommandMsgProcessor::handleMessage(OsMsg& eventMessage)
{
    int msgType = eventMessage.getMsgType();
    // int msgSubType = eventMessage.getMsgSubType();

    if(msgType == OsMsg::PHONE_APP)
        // && msgSubType == CP_SIP_MESSAGE)
    {
        osPrintf("CommandMsgProcessor::handleMessage Got a message\n");
        int messageType = ((SipMessageEvent&)eventMessage).getMessageStatus();

        const SipMessage* sipMsg = ((SipMessageEvent&)eventMessage).getMessage();
        UtlString callId;
        if(sipMsg)
        {
            osPrintf("numRespondToMessages: %d isResponse: %d messageType: %d TransErro: %d\n",
                     numRespondToMessages, sipMsg->isResponse(), messageType,
                     SipMessageEvent::TRANSPORT_ERROR);
            if((numRespondToMessages == -1 || numRespondToMessages > 0) &&
                    !sipMsg->isResponse() && messageType != SipMessageEvent::TRANSPORT_ERROR)
            {
                osPrintf("valid message\n");
                if(numRespondToMessages > 0)
                {
                    numRespondToMessages--;
                }

                SipMessage response;
                if(mpResponseMessage)
                {
                    response = *mpResponseMessage;
                }
                response.setResponseData(sipMsg, responseStatusCode, responseStatusText.data());

                UtlString address;
                int port;
                UtlString protocol;
                UtlString tag;

                sipMsg->getToAddress(&address,
                                     &port,
                                     &protocol,
                                     NULL,
                                     NULL,
                                     &tag) ;

                if( tag.isNull())
                {
                    int tagNum = rand();
                    char tag[100];
                    sprintf(tag, "%d", tagNum);
                    UtlString tagWithDot(tag);
                    tagWithDot.append(".34756498567498567");
                    response.setToFieldTag(tagWithDot);
                }

                UtlString msgBytes;
                int msgLen;
                response.getBytes(&msgBytes, &msgLen);
                osPrintf("%s",msgBytes.data());

                if(mpLastResponseMessage)
                {
                    delete mpLastResponseMessage;
                    mpLastResponseMessage = NULL;
                }
                // Keep a copy of the last response sent
                mpLastResponseMessage = new SipMessage(response);

                if(userAgent->send(response))
                {
                    osPrintf("Sent response\n");
                }
                else
                {
                    osPrintf("Send failed\n");
                }
            }
        }
    }
    return(TRUE);
}
示例#25
0
//functions
UtlBoolean
SubscribeServerThread::handleMessage(OsMsg& eventMessage)
{

    // Only handle SIP messages
    if (eventMessage.getMsgType() != OsMsg::PHONE_APP ||
        eventMessage.getMsgSubType() != SipMessage::NET_SIP_MESSAGE)
    {
       return FALSE ;
    }

    const SipMessage* message =
        ((SipMessageEvent&)eventMessage).getMessage();

    UtlString userKey;
    UtlString uri;
    SipMessage finalResponse;

    // Test for request/response processing code path
    if (!message->isResponse())
    {
        // this is a request, so authenticate and authorize the request
        if ( isValidDomain( message, &finalResponse ) )
        {
            UtlString eventPackage;
            UtlString id;
            UtlHashMap otherParams;

            message->getEventField(&eventPackage, &id, &otherParams);

            StatusPluginReference* pluginContainer =
                mPluginTable->getPlugin( eventPackage );

            if( pluginContainer )
            {
               //check in credential database if authentication needed
               UtlString authenticatedUser, authenticatedRealm;
               if( isAuthenticated ( message, &finalResponse, authenticatedUser, authenticatedRealm ) )
               {
                  if ( isAuthorized ( message, &finalResponse, pluginContainer ) )
                  {
                     // fetch the plugin
                     SubscribeServerPluginBase* plugin =
                        pluginContainer->getPlugin();

                     if (plugin)
                     {
                        int timeNow = (int)OsDateTime::getSecsSinceEpoch();
                        int grantedExpiration;
                        UtlString newToTag;

                        // add the subscription to the IMDB
                        SubscribeStatus isSubscriptionAdded
                           = addSubscription(timeNow,
                                             message,
                                             mDefaultDomain,
                                             eventPackage,
                                             id,
                                             otherParams,
                                             newToTag,
                                             grantedExpiration);

                        otherParams.destroyAll();

                        switch ( isSubscriptionAdded )
                        {
                        case STATUS_SUCCESS:
                           // create response - 202 Accepted Response
                           finalResponse.setResponseData( message,
                                                          SIP_ACCEPTED_CODE,
                                                          SIP_ACCEPTED_TEXT);
                           // Set the granted subscription time.
                           finalResponse.setExpiresField(grantedExpiration);

                           plugin->handleSubscribeRequest( *message,
                                                           finalResponse,
                                                           authenticatedUser.data(),
                                                           authenticatedRealm.data(),
                                                           mDefaultDomain.data());

                           // ensure that the contact returned will route back to here
                           // (the default supplied by SipUserAgent will not).
                           {
                              UtlString requestUri;
                              message->getRequestUri(&requestUri);
                              finalResponse.setContactField(requestUri);
                           }
                           break;

                        case STATUS_TO_BE_REMOVED:
                           // create response - 202 Accepted Response
                           finalResponse.setResponseData( message,
                                                          SIP_ACCEPTED_CODE,
                                                          SIP_ACCEPTED_TEXT);
                           // Set the granted subscription time.
                           finalResponse.setExpiresField(grantedExpiration);

                           plugin->handleSubscribeRequest( *message,
                                                           finalResponse,
                                                           authenticatedUser.data(),
                                                           authenticatedRealm.data(),
                                                           mDefaultDomain.data());

                           // ensure that the contact returned will route back to here
                           // (the default supplied by SipUserAgent will not).
                           {
                              UtlString requestUri;
                              message->getRequestUri(&requestUri);
                              finalResponse.setContactField(requestUri);
                           }
                           // Now that final NOTIFY has been sent, remove row
                           removeSubscription(message);

                           break;

                        case STATUS_LESS_THAN_MINEXPIRES:
                           // (already logged in addSubscription)

                           // send 423 Subscription Too Brief response
                           finalResponse.setResponseData(
                              message,
                              SIP_TOO_BRIEF_CODE,
                              SIP_TOO_BRIEF_TEXT );

                           finalResponse.setHeaderValue(
                              SIP_MIN_EXPIRES_FIELD,
                              mMinExpiresTimeStr,
                              0 );
                           break;

                        case STATUS_INVALID_REQUEST:
                           OsSysLog::add(FAC_SIP, PRI_ERR,
                                         "SubscribeServerThread::handleMessage()"
                                         "Subscription Could Not Be Added "
                                         SIP_BAD_REQUEST_TEXT
                              );

                           finalResponse.setResponseData(
                              message,
                              SIP_BAD_REQUEST_CODE,
                              SIP_BAD_REQUEST_TEXT );
                           break;

                        case STATUS_FORBIDDEN:
                           OsSysLog::add(FAC_SIP, PRI_ERR,
                                         "SubscribeServerThread::handleMessage()"
                                         "Subscription Could Not Be Added "
                                         SIP_FORBIDDEN_TEXT
                              );

                           finalResponse.setResponseData(
                              message,
                              SIP_FORBIDDEN_CODE,
                              SIP_FORBIDDEN_TEXT);
                           break;

                        case STATUS_NOT_FOUND:
                           OsSysLog::add(FAC_SIP, PRI_ERR,
                                         "SubscribeServerThread::handleMessage()"
                                         "Subscription Could Not Be Added "
                                         SIP_NOT_FOUND_TEXT
                              );
                           finalResponse.setResponseData(
                              message,
                              SIP_NOT_FOUND_CODE,
                              SIP_NOT_FOUND_TEXT );
                           break;

                        case STATUS_BAD_SUBSCRIPTION:
                           // send 481 Subscription Does Not Exist response
                           OsSysLog::add(FAC_SIP, PRI_DEBUG,
                                         "SubscribeServerThread::handleMessage()"
                                         "Subscription to be renewed does not exist "
                                         SIP_BAD_SUBSCRIPTION_TEXT
                              );
                           finalResponse.setResponseData(
                              message,
                              SIP_BAD_SUBSCRIPTION_CODE,
                              SIP_BAD_SUBSCRIPTION_TEXT );
                           break;

                        case STATUS_INTERNAL_ERROR:
                        default:
                           OsSysLog::add(FAC_SIP, PRI_ERR,
                                         "SubscribeServerThread::handleMessage()"
                                         "Subscription Could Not Be Added "
                                         "Status %d from addSubscription",
                                         isSubscriptionAdded
                              );
                           finalResponse.setResponseData(
                              message,
                              SIP_SERVER_INTERNAL_ERROR_CODE,
                              "Subscription database error" );
                        }

                        // Apply the new to-tag, if any, to the response.
                        if (!newToTag.isNull())
                        {
                           finalResponse.setToFieldTag(newToTag);
                        }
                     }
                     else
                     {
                        OsSysLog::add(FAC_SIP, PRI_CRIT,
                                      "SubscribeServerThread::handleMessage()"
                                      " container->getPlugin failed for '%s'",
                                      eventPackage.data()
                           );
                        finalResponse.setResponseData(
                           message,
                           SIP_SERVER_INTERNAL_ERROR_CODE,
                           SIP_SERVER_INTERNAL_ERROR_TEXT );
                     }
                  }
                  else
                  {
                     // not authorized - the response was created in isAuthorized
                  }
               }
               else
               {
                  // not authenticated - the response was created in isAuthenticated
               }
            }
            else // no plugin found for this event type
            {
               OsSysLog::add(FAC_SIP, PRI_WARNING,
                             "SubscribeServerThread::handleMessage()"
                             " Request denied - "
                             SIP_BAD_EVENT_TEXT
                  );
               finalResponse.setResponseData( message,
                                              SIP_BAD_EVENT_CODE,
                                              "Event type not supported" );
            }

            // send final response
            UtlString finalMessageStr;
            ssize_t finalMessageLen;
            finalResponse.getBytes(&finalMessageStr, &finalMessageLen);
            OsSysLog::add(FAC_SIP, PRI_DEBUG, "\n----------------------------------\n"
                "Sending final response\n%s",finalMessageStr.data());
            mpSipUserAgent->setUserAgentHeader( finalResponse );
            mpSipUserAgent->send( finalResponse );
        }
        else // Invalid domain
        {
           const char* notFoundMsg = SIP_NOT_FOUND_TEXT " Invalid Domain";
           finalResponse.setResponseData(message,
                                         SIP_NOT_FOUND_CODE,
                                         notFoundMsg
                                         );
           mpSipUserAgent->setUserAgentHeader( finalResponse );
           mpSipUserAgent->send( finalResponse );
        }
    }
    else // response
    {
       // The server may send us back a "481" response, if it does we need
       // to remove the subscription from the SubscriptionDB as the callid
       // that it corresponds to is stale (probably the phone was rebooted)
       // In the above case, RFC 3265 says we MUST remove the subscription.
       // It also says (essentially) that any error that does not imply a retry
       // SHOULD remove the subscription.  We will interpret this to be any
       // 4xx code _except_ 408 timeout (because that may be a transient error).
       int responseCode = message->getResponseStatusCode();
       if (   responseCode >= SIP_4XX_CLASS_CODE
           && responseCode != SIP_REQUEST_TIMEOUT_CODE )
       {
          // remove the subscription
          removeErrorSubscription ( *message );
       }
    }
    return TRUE;
}
示例#26
0
OsStatus EmailNotifier::handleAlarm(const OsTime alarmTime,
      const UtlString& callingHost,
      const cAlarmData* alarmData,
      const UtlString& alarmMsg)
{
   OsStatus retval = OS_FAILED;

   //execute the mail command for each user
   UtlString groupKey(alarmData->getGroupName());
   if (!groupKey.isNull())
   {
      UtlContainable* pContact = mContacts.findValue(&groupKey);
      if (pContact)
      {
         // Process the comma separated list of contacts
         UtlString* contactList = dynamic_cast<UtlString*> (pContact);
         if (!contactList->isNull())
         {
            MailMessage message(mEmailStrFrom, mReplyTo, mSmtpServer);
            UtlTokenizer tokenList(*contactList);

            UtlString entry;
            while (tokenList.next(entry, ","))
            {
               message.To(entry, entry);
            }

            UtlString body;
            UtlString tempStr;

            body = mEmailStrIntro;
            body.append("\n");

            assembleMsg(mEmailStrAlarm, alarmData->getCode(), tempStr);
            body.append(tempStr);
            body.append("\n");

            assembleMsg(mEmailStrHost, callingHost, tempStr);
            body.append(tempStr);
            body.append("\n");

            OsDateTime logTime(alarmTime);
            UtlString strTime;
            logTime.getIsoTimeStringZus(strTime);
            assembleMsg(mEmailStrTime, strTime, tempStr);
            body.append(tempStr);
            body.append("\n");

            UtlString sevStr = OsSysLog::priorityName(alarmData->getSeverity());
            assembleMsg(mEmailStrSeverity, sevStr, tempStr);
            body.append(tempStr);
            body.append("\n");
            assembleMsg(mEmailStrDescription, alarmMsg, tempStr);
            body.append(tempStr);
            body.append("\n");
            assembleMsg(mEmailStrResolution, alarmData->getResolution(), tempStr);
            body.append(tempStr);
            OsSysLog::add(FAC_ALARM, PRI_DEBUG, "AlarmServer: email body is %s", body.data());

            message.Body(body);

            UtlSList subjectParams;
            UtlString codeStr(alarmData->getCode());
            UtlString titleStr(alarmData->getShortTitle());
            subjectParams.append(&codeStr);
            subjectParams.append(&titleStr);
            assembleMsg(mEmailStrSubject, subjectParams, tempStr);
            message.Subject(tempStr);

            // delegate send to separate task so as not to block
            EmailSendTask::getInstance()->sendMessage(message);
         }
      }
   }

   return retval;
}
示例#27
0
void OsSSL::logConnectParams(const OsSysLogFacility facility, ///< callers facility
                             const OsSysLogPriority priority, ///< log priority
                             const char* callerMsg,  ///< Identifies circumstances of connection
                             SSL*  connection  ///< SSL connection to be described
                             )
{
   if (connection)
   {
      char* subjectStr = NULL;
      char* issuerStr = NULL;

      UtlString altNames;

      // Extract the subject and issuer information about the peer
      // and the certificate validation result.  Neither of these
      // are meaningful without the other.
      //    (note various dynamically allocated items - freed below)
      int   validity  = SSL_get_verify_result(connection);
      X509* peer_cert = SSL_get_peer_certificate(connection);
      if (peer_cert)
      {
         subjectStr = X509_NAME_oneline(X509_get_subject_name(peer_cert),0,0);
         issuerStr = X509_NAME_oneline(X509_get_issuer_name(peer_cert),0,0);

         // Look for the subjectAltName URI or DNS attributes
         GENERAL_NAMES* names;
         names = (GENERAL_NAMES*)X509_get_ext_d2i(peer_cert, NID_subject_alt_name, NULL, NULL);
         for(int i = 0; i < sk_GENERAL_NAME_num(names); i++)
         {
            GENERAL_NAME* name = sk_GENERAL_NAME_value(names, i);

            switch (name->type)
            {
            case GEN_DNS:
            {
               ASN1_IA5STRING* uri = name->d.uniformResourceIdentifier;
               if (!altNames.isNull())
               {
                  altNames.append(",");
               }
               altNames.append((const char*)(uri->data),uri->length);
            }
            break;

            case GEN_URI:
            {
               ASN1_IA5STRING* uri = name->d.uniformResourceIdentifier;
               if (!altNames.isNull())
               {
                  altNames.append(",");
               }
               altNames.append((const char*)(uri->data),uri->length);
            }
            break;

            default:
               // don't care about any other values
               break;
            }
         }
         sk_GENERAL_NAME_pop_free(names, GENERAL_NAME_free);
      }

      // Get the name of the encryption applied to the connection
      const char* cipher = SSL_get_cipher(connection);

      OsSysLog::add(FAC_KERNEL, PRI_DEBUG,
                    "%s SSL Connection:\n"
                    "   status:  %s\n"
                    "   peer:    '%s'\n"
                    "   alt names: %s\n"
                    "   cipher:  '%s'\n"
                    "   issuer:  '%s'",
                    callerMsg,
                    validity == X509_V_OK ? "Verified" : "NOT VERIFIED",
                    subjectStr ? subjectStr : "",
                    altNames.isNull() ? "" : altNames.data(),
                    cipher     ? cipher     : "",
                    issuerStr  ? issuerStr  : ""
                    );

      // Release the various dynamic things
      if (subjectStr)
      {
         OPENSSL_free(subjectStr);
      }
      if (issuerStr)
      {
         OPENSSL_free(issuerStr);
      }
      if (peer_cert)
      {
         X509_free(peer_cert);
      }
   }
   else
   {
      OsSysLog::add(FAC_KERNEL, PRI_ERR,
                    "OsSSL::logConnectParams called by %s with NULL connection",
                    callerMsg
                    );
   }
}
示例#28
0
//
// Pull out important parameters from the config DB.
// These parameters are set at runtime and cannot be changed without a restart.
//
UtlBoolean ParkService::loadConfig(
    int& UdpPort,
    int& TcpPort,
    int& RtpBase,
    UtlString& bindIp,
    int& MaxSessions,
    UtlBoolean& OneButtonBLF,
    UtlString&   domain,
    UtlString&   realm,
    UtlString&   user,
    SipLineMgr* lineMgr,
    int& Lifetime,
    int& BlindXferWait,
    int& KeepAliveTime
    )
{
   UtlBoolean ret = true;

   // SipXecsService owns the main configDb
   OsConfigDb& configDb = getConfigDb();

    // Read the user agent parameters from the config file.
    if (configDb.get(CONFIG_SETTING_UDP_PORT, UdpPort) != OS_SUCCESS)
        UdpPort = PARK_DEFAULT_UDP_PORT;

    if (configDb.get(CONFIG_SETTING_TCP_PORT, TcpPort) != OS_SUCCESS)
        TcpPort = PARK_DEFAULT_TCP_PORT;

    if (configDb.get(CONFIG_SETTING_RTP_PORT, RtpBase) != OS_SUCCESS)
        RtpBase = DEFAULT_RTP_PORT;

    if (configDb.get(CONFIG_SETTING_BIND_IP, bindIp) != OS_SUCCESS ||
            !OsSocket::isIp4Address(bindIp))
        bindIp = PARK_DEFAULT_BIND_IP;

    if (configDb.get(CONFIG_SETTING_MAX_SESSIONS, MaxSessions) != OS_SUCCESS)
    {
        MaxSessions = DEFAULT_MAX_SESSIONS;
    }

    OneButtonBLF =
       configDb.getBoolean(CONFIG_SETTING_ONE_BUTTON_BLF, DEFAULT_ONE_BUTTON_BLF);

    OsConfigDb  domainConfiguration;
    OsPath      domainConfigPath = SipXecsService::domainConfigPath();

    if (OS_SUCCESS == domainConfiguration.loadFromFile(domainConfigPath.data()))
    {
       domainConfiguration.get(SipXecsService::DomainDbKey::SIP_DOMAIN_NAME, domain);
       domainConfiguration.get(SipXecsService::DomainDbKey::SIP_REALM, realm);

       if (!domain.isNull() && !realm.isNull())
       {
          CredentialDB* credentialDb;
          if ((credentialDb = CredentialDB::getInstance()))
          {
             Url identity;

             identity.setUserId(PARK_SERVER_ID_TOKEN);
             identity.setHostAddress(domain);

             UtlString ha1_authenticator;
             UtlString authtype;

             if (credentialDb->getCredential(identity, realm, user, ha1_authenticator, authtype))
             {
                if ((lineMgr = new SipLineMgr()))
                {
                   SipLine line(identity // user entered url
                                ,identity // identity url
                                ,user     // user
                                ,TRUE     // visible
                                ,SipLine::LINE_STATE_PROVISIONED
                                ,TRUE     // auto enable
                                ,FALSE    // use call handling
                      );

                   if (lineMgr->addLine(line))
                   {
                      lineMgr->startLineMgr();
                      if (lineMgr->addCredentialForLine( identity, realm, user, ha1_authenticator
                                                        ,HTTP_DIGEST_AUTHENTICATION
                             )
                         )
                      {
                         OsSysLog::add(LOG_FACILITY, PRI_INFO,
                                       "Added identity '%s': user='******' realm='%s'"
                                       ,identity.toString().data(), user.data(), realm.data()
                            );
                      }
                      else
                      {
                         OsSysLog::add(LOG_FACILITY, PRI_ERR,
                                       "Error adding identity '%s': user='******' realm='%s'\n"
                                       "  escape and timeout from park may not work.",
                                       identity.toString().data(), user.data(), realm.data()
                            );
                      }

                      lineMgr->setDefaultOutboundLine(identity);
                   }     // end addLine
                   else
                   {
                      OsSysLog::add(LOG_FACILITY, PRI_ERR,
                                    "addLine failed: "
                                    "  escape and timeout from park may not work."
                         );
                   }
                }
                else
                {
                   OsSysLog::add(LOG_FACILITY, PRI_ERR,
                                 "Constructing SipLineMgr failed:  "
                                 "  escape and timeout from park may not work."
                      );
                }
             }  // end getCredential
             else
             {
                OsSysLog::add(LOG_FACILITY, PRI_ERR,
                              "No credential found for '%s@%s' in realm '%s'"
                              "; transfer functions will not work",
                              PARK_SERVER_ID_TOKEN, domain.data(), realm.data()
                              );
             }

             credentialDb->releaseInstance();
          }   // end credentialDB
          else
          {
             OsSysLog::add(LOG_FACILITY, PRI_ERR,
                           "Failed to open credentials database"
                           "; transfer functions will not work"
                           );
          }
       }    // end have domain and realm
       else
       {
          OsSysLog::add(LOG_FACILITY, PRI_ERR,
                        "Domain or Realm not configured:"
                        "\n  '%s' : '%s'\n  '%s' : '%s'"
                        "  transfer functions will not work.",
                        SipXecsService::DomainDbKey::SIP_DOMAIN_NAME, domain.data(),
                        SipXecsService::DomainDbKey::SIP_REALM, realm.data()
                        );
       }
    }       // end found domain config
    else
    {
       OsSysLog::add(LOG_FACILITY, PRI_ERR,
                     "main: failed to load domain configuration from '%s'",
                     domainConfigPath.data()
                     );
    }

    // Read Park Server parameters from the config file.
    if (configDb.get(CONFIG_SETTING_LIFETIME, Lifetime) != OS_SUCCESS)
    {
       Lifetime = DEFAULT_LIFETIME;
    }
    if (configDb.get(CONFIG_SETTING_BLIND_WAIT, BlindXferWait) != OS_SUCCESS)
    {
       BlindXferWait = DEFAULT_BLIND_WAIT;
    }
    if (configDb.get(CONFIG_SETTING_KEEPALIVE_TIME, KeepAliveTime) != OS_SUCCESS)
    {
       KeepAliveTime = DEFAULT_KEEPALIVE_TIME;
    }

   return ret;
}
示例#29
0
// Constructor
SipRegistrar::SipRegistrar(OsConfigDb* configDb) :
   OsServerTask("SipRegistrar", NULL, SIPUA_DEFAULT_SERVER_OSMSG_QUEUE_SIZE),
   mConfigDb(configDb),
   mSipUserAgent(NULL),
   mRedirectServer(NULL),
   mRedirectMsgQ(NULL),
   // Create the SipRegistrarServer object so it will be available immediately,
   // but don't start the associated thread until the registrar is operational.
   mRegistrarServer(new SipRegistrarServer(*this)),
   mRegistrarMsgQ(NULL),
   mRegisterEventServer(NULL),
   mRegistrarPersist(NULL),
   mpRegDb(NULL),
   mpSubscribeDb(NULL),
   mpEntityDb(NULL)
{
   Os::Logger::instance().log(FAC_SIP, PRI_DEBUG, "SipRegistrar::SipRegistrar constructed.");


   // Some phones insist (incorrectly) on putting the proxy port number on urls;
   // we get it from the configuration so that we can ignore it.
   mProxyNormalPort = mConfigDb->getPort("SIP_REGISTRAR_PROXY_PORT");
   if (mProxyNormalPort == PORT_DEFAULT)
   {
      mProxyNormalPort = SIP_PORT;
   }

   // Domain Name
   mConfigDb->get("SIP_REGISTRAR_DOMAIN_NAME", mDefaultDomain);
   if ( mDefaultDomain.isNull() )
   {
      OsSocket::getHostIp(&mDefaultDomain);
      Os::Logger::instance().log(FAC_SIP, PRI_CRIT,
                    "SIP_REGISTRAR_DOMAIN_NAME not configured using IP '%s'",
                    mDefaultDomain.data()
                    );
   }
   // get the url parts for the domain
   Url defaultDomainUrl(mDefaultDomain);
   mDefaultDomainPort = defaultDomainUrl.getHostPort();
   defaultDomainUrl.getHostAddress(mDefaultDomainHost);
   // make sure that the unspecified domain name is also valid
   addValidDomain(mDefaultDomainHost, mDefaultDomainPort);

   // read the domain configuration
   OsConfigDb domainConfig;
   domainConfig.loadFromFile(SipXecsService::domainConfigPath());


   // Domain Aliases
   //   (other domain names that this registrar accepts as valid in the request URI)
   UtlString domainAliases;
   domainConfig.get(SipXecsService::DomainDbKey::SIP_DOMAIN_ALIASES, domainAliases);

   if (!domainAliases.isNull())
   {
      Os::Logger::instance().log(FAC_SIP, PRI_DEBUG, "SipRegistrar::SipRegistrar "
                    "SIP_DOMAIN_ALIASES : %s", domainAliases.data());
   }
   else
   {
      Os::Logger::instance().log(FAC_SIP, PRI_ERR, "SipRegistrar::SipRegistrar "
                    "SIP_DOMAIN_ALIASES not found.");
   }

   UtlString aliasString;
   int aliasIndex = 0;
   while(NameValueTokenizer::getSubField(domainAliases.data(), aliasIndex,
                                         ", \t", &aliasString))
   {
      Url aliasUrl(aliasString);
      UtlString hostAlias;
      aliasUrl.getHostAddress(hostAlias);
      int port = aliasUrl.getHostPort();

      addValidDomain(hostAlias,port);
      aliasIndex++;
   }

   mongo::ConnectionString mongoConn = MongoDB::ConnectionInfo::connectionStringFromFile();
   mpRegDb = new RegDB(MongoDB::ConnectionInfo(mongoConn, RegDB::NS));
   mpSubscribeDb = new SubscribeDB(MongoDB::ConnectionInfo(mongoConn, SubscribeDB::NS));
   mpEntityDb = new EntityDB(MongoDB::ConnectionInfo(mongoConn, EntityDB::NS));

   mConfigDb->get("SIP_REGISTRAR_BIND_IP", mBindIp);
   if ((mBindIp.isNull()) || !OsSocket::isIp4Address(mBindIp))
   {
	  mBindIp = "0.0.0.0";
   }
}
示例#30
0
//
// Create the real Server, passing in the configured parameters
//
void ParkService::run()
{
    int UdpPort;
    int TcpPort;
    int RtpBase;
    UtlString bindIp;
    int MaxSessions;
    UtlBoolean OneButtonBLF;
    UtlString   domain;
    UtlString   realm;
    UtlString   user;
    SipLineMgr* lineMgr = NULL;
    int Lifetime;
    int BlindXferWait;
    int KeepAliveTime;

   loadConfig(
       UdpPort,
       TcpPort,
       RtpBase,
       bindIp,
       MaxSessions,
       OneButtonBLF,
       domain,
       realm,
       user,
       lineMgr,
       Lifetime,
       BlindXferWait,
       KeepAliveTime
       );

   // initialize other pieces

    // This is not configurable, as consultative transfers should
    // succeed or fail immediately.
    int ConsXferWait;
    ConsXferWait = CONS_XFER_WAIT;

    // Bind the SIP user agent to a port and start it up
    SipUserAgent* userAgent = new SipUserAgent(TcpPort,
                                               UdpPort,
                                               TcpPort+1,
                                               NULL, // publicAddress
                                               user.isNull() ? NULL : user.data(), // default user
                                               bindIp,
                                               domain.isNull() ? NULL : domain.data(), // outbound proxy
                                               NULL, // sipDirectoryServers (deprecated)
                                               NULL, // sipRegistryServers (deprecated)
                                               NULL, // authenicateRealm
                                               NULL, // authenticateDb
                                               NULL, // authorizeUserIds (deprecated)
                                               NULL, // authorizePasswords (deprecated)
                                               lineMgr
                                               );
    userAgent->setUserAgentHeaderProperty("sipXecs/park");
    userAgent->start();

    if (!userAgent->isOk())
    {
       OsSysLog::add(LOG_FACILITY, PRI_EMERG, "SipUserAgent failed to initialize, requesting shutdown");
       setShutdownFlag(true);
    }

    // Read the list of codecs from the configuration file.
    SdpCodecFactory codecFactory;
    initCodecs(&codecFactory, &getConfigDb());

    // Initialize and start up the media subsystem
    mpStartUp(MP_SAMPLE_RATE, MP_SAMPLES_PER_FRAME, 6 * MaxSessions, &getConfigDb());
    MpMediaTask::getMediaTask(MaxSessions);

#ifdef INCLUDE_RTCP
    CRTCManager::getRTCPControl();
#endif //INCLUDE_RTCP

    mpStartTasks();

    // Instantiate the call processing subsystem
    UtlString localAddress;
    int localPort ;
    userAgent->getLocalAddress(&localAddress, &localPort) ;
    if (localAddress.isNull())
        OsSocket::getHostIp(&localAddress);

    // Construct an address to be used in outgoing requests (primarily
    // INVITEs stimulated by REFERs).
    UtlString outgoingAddress;
    {
       char buffer[100];
       sprintf(buffer, "sip:sipXpark@%s:%d", localAddress.data(),
               portIsValid(UdpPort) ? UdpPort : TcpPort);
       outgoingAddress = buffer;
    }
    CallManager callManager(FALSE,
                           NULL,
                           TRUE,                              // early media in 180 ringing
                           &codecFactory,
                           RtpBase,                           // rtp start
                           RtpBase + (2 * MaxSessions),       // rtp end
                           localAddress,
                           localAddress,
                           userAgent,
                           0,                                 // sipSessionReinviteTimer
                           NULL,                              // mgcpStackTask
                           outgoingAddress,                   // defaultCallExtension
                           Connection::RING,                  // availableBehavior
                           NULL,                              // unconditionalForwardUrl
                           -1,                                // forwardOnNoAnswerSeconds
                           NULL,                              // forwardOnNoAnswerUrl
                           Connection::BUSY,                  // busyBehavior
                           NULL,                              // sipForwardOnBusyUrl
                           NULL,                              // speedNums
                           CallManager::SIP_CALL,             // phonesetOutgoingCallProtocol
                           4,                                 // numDialPlanDigits
                           CallManager::NEAR_END_HOLD,        // holdType
                           5000,                              // offeringDelay
                           "",                                // pLocal
                           CP_MAXIMUM_RINGING_EXPIRE_SECONDS, // inviteExpiresSeconds
                           QOS_LAYER3_LOW_DELAY_IP_TOS,       // expeditedIpTos
                           MaxSessions,                       // maxCalls
                           sipXmediaFactoryFactory(NULL));    // CpMediaInterfaceFactory



    // Create a listener (application) to deal with call
    // processing events (e.g. incoming call and hang ups)
    OrbitListener listener(&callManager, Lifetime, BlindXferWait, KeepAliveTime, ConsXferWait);

    callManager.addTaoListener(&listener);
    listener.start();

    // Create the SIP Subscribe Server
    SipPersistentSubscriptionMgr
       subscriptionMgr(SUBSCRIPTION_COMPONENT_PARK,
                       domain,
                       "subscription"); // Component for holding the subscription data
    SipSubscribeServerEventHandler policyHolder; // Component for granting the subscription rights
    SipPublishContentMgr publisher; // Component for publishing the event contents

    SipSubscribeServer subscribeServer(SipSubscribeServer::terminationReasonSilent,
                                       *userAgent, publisher,
                                       subscriptionMgr, policyHolder);
    subscribeServer.enableEventType(DIALOG_EVENT_TYPE, NULL, NULL, NULL,
                                    SipSubscribeServer::standardVersionCallback,
                                    TRUE // dialogEvents only produces full content.
       );
    subscribeServer.start();

    // Create the DialogEventPublisher.
    // Use the sipX domain as the hostport of resource-IDs of the
    // published events, as that will be the request-URIs of SUBSCRIBEs.
    DialogEventPublisher dialogEvents(&callManager, &publisher, domain, PORT_NONE, OneButtonBLF);
    callManager.addTaoListener(&dialogEvents);
    dialogEvents.start();

    // Start up the call processing system
    callManager.start();

    // Loop forever until signaled to shut down

    int numTwoSecIntervals = 0;
    int CleanLoopWaitTimeSecs = 10;

    while (!getShutdownFlag())
    {
       OsTask::delay(2000);

       if (2*numTwoSecIntervals >= CleanLoopWaitTimeSecs)
       {
           numTwoSecIntervals = 0;
           if (OsSysLog::willLog(FAC_PARK, PRI_DEBUG))
           {
               OsSysLog::add(LOG_FACILITY, PRI_DEBUG,
                             "park main "
                             "logging call status"
                             );
               callManager.printCalls(0) ;
               listener.dumpCallsAndTransfers();
           }
       }
       else
       {
           numTwoSecIntervals += 1;
       }

    }

}