Exemple #1
0
RegStore::AoR* RegistrationTimeoutHandler::set_aor_data(RegStore* current_store,
                                                        std::string aor_id,
                                                        RegStore::AoR* previous_aor_data,
                                                        RegStore* remote_store,
                                                        bool is_primary,
                                                        bool& all_bindings_expired)
{
  RegStore::AoR* aor_data = NULL;
  bool previous_aor_data_alloced = false;

  do
  {
    if (!reg_store_access_common(&aor_data, previous_aor_data_alloced, aor_id,
                                 current_store, remote_store, &previous_aor_data, trail()))
    {
      // LCOV_EXCL_START - local store (used in testing) never fails
      break;
      // LCOV_EXCL_STOP
    }
  }
  while (!current_store->set_aor_data(aor_id, aor_data, is_primary, trail(), all_bindings_expired));

  // If we allocated the AoR, tidy up.
  if (previous_aor_data_alloced)
  {
    delete previous_aor_data;
  }

  return aor_data;
}
Exemple #2
0
void AuthTimeoutHandler::run()
{
  if (_req.method() != htp_method_POST)
  {
    send_http_reply(HTTP_BADMETHOD);
    delete this;
    return;
  }

  SAS::Marker start_marker(trail(), MARKER_ID_START, 1u);
  SAS::report_marker(start_marker);
  SAS::Marker calling_dn(trail(), MARKER_ID_CALLING_DN, 1u);
  calling_dn.add_var_param(_impu);
  SAS::report_marker(calling_dn);

  HTTPCode rc = handle_response(_req.body());

  SAS::Marker end_marker(trail(), MARKER_ID_END, 1u);
  SAS::report_marker(end_marker);

  if (rc != HTTP_OK)
  {
    LOG_DEBUG("Unable to handle callback from Chronos");
    send_http_reply(rc);
    delete this;
    return;
  }

  send_http_reply(HTTP_OK);
  delete this;
}
Exemple #3
0
void AuthTimeoutTask::run()
{
  if (_req.method() != htp_method_POST)
  {
    send_http_reply(HTTP_BADMETHOD);
    delete this;
    return;
  }

  SAS::Marker start_marker(trail(), MARKER_ID_START, 1u);
  SAS::report_marker(start_marker);

  HTTPCode rc = handle_response(_req.get_rx_body());

  SAS::Marker end_marker(trail(), MARKER_ID_END, 1u);
  SAS::report_marker(end_marker);

  if (rc != HTTP_OK)
  {
    LOG_DEBUG("Unable to handle callback from Chronos");
    send_http_reply(rc);
    delete this;
    return;
  }

  send_http_reply(HTTP_OK);
  delete this;
}
Exemple #4
0
void BillingTask::run()
{
  if (_req.method() != htp_method_POST)
  {
    send_http_reply(405);
    delete this;
    return;
  }

  bool timer_interim = false;
  if (_req.param(TIMER_INTERIM_PARAM) == "true")
  {
    timer_interim = true;
    SAS::Marker cid_assoc(trail(), MARKER_ID_SIP_CALL_ID, 0);
    cid_assoc.add_var_param(call_id());
    SAS::report_marker(cid_assoc);

    SAS::Event timer_pop(trail(), SASEvent::INTERIM_TIMER_POPPED, 0);
    SAS::report_event(timer_pop);
  }

  Message* msg = NULL;
  HTTPCode rc = parse_body(call_id(), timer_interim, _req.get_rx_body(), &msg, trail());

  if (rc != HTTP_OK)
  {
    SAS::Event rejected(trail(), SASEvent::REQUEST_REJECTED_INVALID_JSON, 0);
    SAS::report_event(rejected);
    send_http_reply(rc);
  }
  else
  {
    if (msg != NULL)
    {
      TRC_DEBUG("Handle the received message");

      // The session manager takes ownership of the message object and is
      // responsible for deleting it.
      _sess_mgr->handle(msg);
      msg = NULL;
    }

    // The HTTP reply won't be sent until afer we leave this function, so by
    // putting this last we ensure that the load monitor will get a sensible
    // value for the latency
    send_http_reply(rc);
  }

  delete this;
}
void ICSCFSproutletTsx::on_rx_cancel(int status_code, pjsip_msg* cancel_req)
{
  // If this is cancelling a terminating INVITE then check whether we need to
  // update our session establishment stats.
  if (!_originating &&
      (_req_type == PJSIP_INVITE_METHOD) &&
      (!_session_set_up))
  {
    // Session has failed to establish but for a reason that is not the fault
    // of the network.
    _icscf->_session_establishment_tbl->increment_attempts();
    _icscf->_session_establishment_tbl->increment_failures();
    _icscf->_session_establishment_network_tbl->increment_attempts();
    _icscf->_session_establishment_network_tbl->increment_successes();

    // Set _session_set_up to true so that we don't count this session again
    // when we receive the subsequent final response.
    _session_set_up = true;
  }

  if ((status_code == PJSIP_SC_REQUEST_TERMINATED) &&
      (cancel_req != NULL))
  {
    // Create and send an ACR for the CANCEL request.
    ACR* acr = _icscf->get_acr(trail());

    // @TODO - timestamp from request.
    acr->rx_request(cancel_req);
    acr->send();

    delete acr;
  }
}
Exemple #6
0
History makeHistory(LifeList *cells, int ngenerations) {

    int i;
    History hist;

    hist.cellList= (Cell **)calloc(sizeof(Cell *), ngenerations);
    hist.ncells= (int *)calloc(sizeof(int), ngenerations);
    hist.ngenerations= ngenerations;
    hist.ntrail=0;

    setValues(cells->cellList, cells->ncells, 1);

    for (i=0; i<ngenerations; i++) {
       hist.cellList[i]=(Cell *)calloc(sizeof(Cell), cells->ncells+1);

       hist.ncells[i]=
          copyList(cells->cellList, cells->ncells, hist.cellList[i], 0);

       makeWorkSpace(hist.ntrail+hist.ncells[i]);

       hist.ntrail=trail(cells, 1, scratch2, hist.ntrail, i);
    }

    hist.trail=(Cell *)calloc(sizeof(Cell *), hist.ntrail+1);
    copyList(scratch2, hist.ntrail, hist.trail, 0);

    return hist;
}
Exemple #7
0
/* remove trailing blanks and tabs, and delete blank lines */
int main() {
    char line[MAXLINE];     /* curreent input line */
    while ( rline(line, MAXLINE) > 0 )
        if (trail(line) > 0)
            printf("%s", line);
    return 0;
}
Exemple #8
0
void RegistrationTimeoutTask::handle_response()
{
  bool all_bindings_expired = false;
  RegStore::AoR* aor_data = set_aor_data(_cfg->_store, _aor_id, NULL, _cfg->_remote_store, true, all_bindings_expired);

  if (aor_data != NULL)
  {
    // If we have a remote store, try to store this there too.  We don't worry
    // about failures in this case.
    if (_cfg->_remote_store != NULL)
    {
      bool ignored;
      RegStore::AoR* remote_aor_data = set_aor_data(_cfg->_remote_store, _aor_id, aor_data, NULL, false, ignored);
      delete remote_aor_data;
    }

    if (all_bindings_expired)
    {
      LOG_DEBUG("All bindings have expired based on a Chronos callback - triggering deregistration at the HSS");
      _cfg->_hss->update_registration_state(_aor_id, "", HSSConnection::DEREG_TIMEOUT, 0);
    }
  }
  else
  {
    // We couldn't update the RegStore but there is nothing else we can do to
    // recover from this.
    LOG_INFO("Could not update update RegStore on registration timeout for AoR: %s",
             _aor_id.c_str());
  }

  delete aor_data;
  report_sip_all_register_marker(trail(), _aor_id);
}
/// Mangelwurzel receives an initial request. It will Record-Route itself,
/// strip off all the Via headers and send the request on. It can also change
/// the request in various ways depending on the configuration in its Route
/// header.
/// - It can mangle the dialog identifiers using its mangalgorithm.
/// - It can mangle the Request URI and Contact URI using its mangalgorithm.
/// - It can mangle the To URI using its mangalgorithm.
/// - It can edit the S-CSCF Route header to turn the request into either an
///   originating or terminating request.
/// - It can edit the S-CSCF Route header to turn the request into an out of
///   the blue request.
/// - It can mangle the Record-Route headers URIs.
void MangelwurzelTsx::on_rx_initial_request(pjsip_msg* req)
{
  // Store off the unmodified request.
  _unmodified_request = original_request();

  // If Mangelwurzel receives a REGISTER, we need to respond with a 200 OK
  // rather than mangling the request and forwarding it on.
  if (req->line.req.method.id == PJSIP_REGISTER_METHOD)
  {
    pjsip_msg* rsp = create_response(req, PJSIP_SC_OK);
    send_response(rsp);
    free_msg(req);
    return;
  }

  pj_pool_t* pool = get_pool(req);

  // Get Mangelwurzel's route header and clone the URI. We use this in the SAS
  // event logging that we've received a request, and then we use it to
  // Record-Route ourselves.
  const pjsip_route_hdr* mangelwurzel_route_hdr = route_hdr();
  pjsip_uri* mangelwurzel_uri =
    (pjsip_uri*)pjsip_uri_clone(pool, mangelwurzel_route_hdr->name_addr.uri);

  SAS::Event event(trail(), SASEvent::MANGELWURZEL_INITIAL_REQ, 0);
  event.add_var_param(PJUtils::uri_to_string(PJSIP_URI_IN_ROUTING_HDR,
                                             mangelwurzel_uri));
  SAS::report_event(event);

  if (_config.dialog)
  {
    mangle_dialog_identifiers(req, pool);
  }

  if (_config.req_uri)
  {
    mangle_req_uri(req, pool);
    mangle_contact(req, pool);
  }

  if (_config.to)
  {
    mangle_to(req, pool);
  }

  edit_scscf_route_hdr(req, pool);

  if (_config.routes)
  {
    mangle_record_routes(req, pool);
  }

  strip_via_hdrs(req);

  record_route(req, pool, mangelwurzel_uri);

  send_request(req);
}
Exemple #10
0
void AsChainLink::get_next_application_server(pjsip_msg* msg,
                                              std::string& server_name,
                                              bool& got_dummy_as,
                                              SAS::TrailId msg_trail)
{
  std::vector<Ifc> ifcs = _as_chain->_using_standard_ifcs ?
                          _as_chain->_ifcs.ifcs_list() :
                          _as_chain->_fallback_ifcs;
  got_dummy_as = false;

  while (!complete())
  {
    const Ifc& ifc = ifcs[_index];
    if (ifc.filter_matches(_as_chain->session_case(),
                           _as_chain->_is_registered,
                           false,
                           msg,
                           trail()))
    {
      TRC_DEBUG("Matched iFC %s", to_string().c_str());
      AsInvocation application_server = ifc.as_invocation();

      if (_as_chain->_ifc_configuration._dummy_as != application_server.server_name)
      {
        server_name = application_server.server_name;

        // Store the RequestURI and application server name in the AsInformation
        // structure for this link.
        _as_chain->_as_info[_index].request_uri =
              PJUtils::uri_to_string(PJSIP_URI_IN_REQ_URI, msg->line.req.uri);
        _as_chain->_as_info[_index].as_uri = server_name;

        // Store the default handling as we may need it later.
        _default_handling = application_server.default_handling;

        break;
      }
      else
      {
        TRC_DEBUG("Ignoring this IFC as it matches a dummy AS (%s)",
                  application_server.server_name.c_str());
        SAS::Event event(msg_trail, SASEvent::IFC_MATCHED_DUMMY_AS, 0);
        event.add_var_param(_as_chain->_ifc_configuration._dummy_as);
        SAS::report_event(event);
        got_dummy_as = true;
      }
    }
    ++_index;
  }
}
int main( int ac, char *av[] )
{
	if( ac < 2 )
	{
		usage(av[0]);
		exit(0);
	}
	
	RcCvt cvt;
	trail("#1");
	if( !cvt.init(av[1], av[2]) ){
		fprintf(stderr,"Error in opening files.\n");
		exit(1);
	}
	trail("#2");
	if( !cvt.convert() ){
		fprintf(stderr,"Error in opening files.\n");
		exit(1);
	}
	trail("#3");

	return 0;
}
// LCOV_EXCL_START - TODO add to UTs
void BGCFSproutletTsx::on_rx_cancel(int status_code, pjsip_msg* cancel_req)
{
  if ((status_code == PJSIP_SC_REQUEST_TERMINATED) &&
      (cancel_req != NULL))
  {
    // Create and send an ACR for the CANCEL request.
    ACR* acr = _bgcf->get_acr(trail());

    // @TODO - timestamp from request.
    acr->rx_request(cancel_req);
    acr->send();

    delete acr;
  }
}
Exemple #13
0
/// Apply first AS (if any) to initial request.
//
// See 3GPP TS 23.218, especially s5.2 and s6, for an overview of how
// this works, and 3GPP TS 24.229 s5.4.3.2 and s5.4.3.3 for
// step-by-step details.
//
// @Returns whether processing should stop, continue, or skip to the end.
void AsChainLink::on_initial_request(pjsip_msg* msg,
                                     std::string& server_name,
                                     SAS::TrailId msg_trail)
{
  server_name = "";

  if (_as_chain->trail() != msg_trail)
  {
    // Associate the two trails in SAS so B2BUA calls are displayed properly
    TRC_DEBUG("Asssociating original SAS trail %ld with new message SAS trail %ld", _as_chain->trail(), msg_trail);
    SAS::associate_trails(_as_chain->trail(), msg_trail);
  }

  while (!complete())
  {
    const Ifc& ifc = (_as_chain->_ifcs)[_index];
    if (ifc.filter_matches(_as_chain->session_case(),
                            _as_chain->_is_registered,
                            false,
                            msg,
                            trail()))
    {
      TRC_DEBUG("Matched iFC %s", to_string().c_str());
      AsInvocation application_server = ifc.as_invocation();
      server_name = application_server.server_name;

      // Store the RequestURI and application server name in the AsInformation
      // structure for this link.
      _as_chain->_as_info[_index].request_uri =
            PJUtils::uri_to_string(PJSIP_URI_IN_REQ_URI, msg->line.req.uri);
      _as_chain->_as_info[_index].as_uri = server_name;

      // Store the default handling as we may need it later.
      _default_handling = application_server.default_handling;

      break;
    }
    ++_index;
  }

  return;
}
/// Apply the mangalgorithm to the From tag, To tag (if present) and call ID of
/// req.
void MangelwurzelTsx::mangle_dialog_identifiers(pjsip_msg* req, pj_pool_t* pool)
{
  pjsip_from_hdr* from_hdr = PJSIP_MSG_FROM_HDR(req);

  if (from_hdr != NULL)
  {
    std::string from_tag = PJUtils::pj_str_to_string(&from_hdr->tag);
    mangle_string(from_tag);
    TRC_DEBUG("From tag mangled to %s", from_tag.c_str());
    from_hdr->tag = pj_strdup3(pool, from_tag.c_str());
  }

  pjsip_to_hdr* to_hdr = PJSIP_MSG_TO_HDR(req);

  if (to_hdr != NULL)
  {
    std::string to_tag = PJUtils::pj_str_to_string(&to_hdr->tag);
    mangle_string(to_tag);
    TRC_DEBUG("To tag mangled to %s", to_tag.c_str());
    to_hdr->tag = pj_strdup3(pool, to_tag.c_str());
  }

  pjsip_cid_hdr* cid_hdr = (pjsip_cid_hdr*)pjsip_msg_find_hdr(req,
                                                              PJSIP_H_CALL_ID,
                                                              NULL);
  if (cid_hdr != NULL)
  {
    std::string call_id = PJUtils::pj_str_to_string(&cid_hdr->id);
    mangle_string(call_id);
    TRC_DEBUG("Call ID manged to %s", call_id.c_str());
    cid_hdr->id = pj_strdup3(pool, call_id.c_str());

    // Report a SAS marker for the new call ID so that the two dialogs can be
    // correlated in SAS.
    TRC_DEBUG("Logging SAS Call-ID marker, Call-ID %.*s",
              cid_hdr->id.slen,
              cid_hdr->id.ptr);
    SAS::Marker cid_marker(trail(), MARKER_ID_SIP_CALL_ID, 1u);
    cid_marker.add_var_param(cid_hdr->id.slen, cid_hdr->id.ptr);
    SAS::report_marker(cid_marker, SAS::Marker::Scope::Trace);
  }
}
/// Mangelwurzel receives an in dialog request. It will strip off all the Via
/// headers and send the request on. It can also change the request in various
/// ways depending on the configuration in its Route header.
/// - It can mangle the dialog identifiers using its mangalgorithm.
/// - It can mangle the Request URI and Contact URI using its mangalgorithm.
/// - It can mangle the To URI using its mangalgorithm.
/// - It can edit the S-CSCF Route header to turn the request into either an
///   originating or terminating request.
/// - It can edit the S-CSCF Route header to turn the request into an out of
///   the blue request.
/// - It can mangle the Record-Route headers URIs.
void MangelwurzelTsx::on_rx_in_dialog_request(pjsip_msg* req)
{
  pj_pool_t* pool = get_pool(req);

  // Get the URI from the Route header. We use it in the SAS event logging that
  // we've received an in dialog request.
  const pjsip_route_hdr* mangelwurzel_route_hdr = route_hdr();
  pjsip_uri* mangelwurzel_uri = mangelwurzel_route_hdr->name_addr.uri;

  SAS::Event event(trail(), SASEvent::MANGELWURZEL_IN_DIALOG_REQ, 0);
  event.add_var_param(PJUtils::uri_to_string(PJSIP_URI_IN_ROUTING_HDR,
                                             mangelwurzel_uri));
  SAS::report_event(event);

  if (_config.dialog)
  {
    mangle_dialog_identifiers(req, pool);
  }

  if (_config.req_uri)
  {
    mangle_req_uri(req, pool);
    mangle_contact(req, pool);
  }

  if (_config.to)
  {
    mangle_to(req, pool);
  }

  edit_scscf_route_hdr(req, pool);

  if (_config.routes)
  {
    mangle_routes(req, pool);
  }

  strip_via_hdrs(req);

  send_request(req);
}
Exemple #16
0
main()
	{
		int i=5;
		printf("%d\n",i++*i--);
		
		char c='a';
		printf("%d\n",c);
		int t=((int)c++);
		printf("%d\n",t);
		
		char c1[455];
		char *p;
		gets(c1);
		
		for(p=c1;*p!='\0';p++);
		printf("%d",p-c1);
			char p2[100];
		printf("\n\nmax%d\n\n",trail(p2,10));				
			
		
	
	}
Exemple #17
0
/// Apply first AS (if any) to initial request.
//
// See 3GPP TS 23.218, especially s5.2 and s6, for an overview of how
// this works, and 3GPP TS 24.229 s5.4.3.2 and s5.4.3.3 for
// step-by-step details.
//
// @Returns whether processing should stop, continue, or skip to the end.
AsChainLink::Disposition AsChainLink::on_initial_request(pjsip_tx_data* tdata,
                                                         std::string& server_name)
{
  // Store the RequestURI in the AsInformation structure for this link.
  _as_chain->_as_info[_index].request_uri =
        PJUtils::uri_to_string(PJSIP_URI_IN_REQ_URI, tdata->msg->line.req.uri);

  if (complete())
  {
    LOG_DEBUG("No ASs left in chain");
    return AsChainLink::Disposition::Complete;
  }

  const Ifc& ifc = (_as_chain->_ifcs)[_index];
  if (!ifc.filter_matches(_as_chain->session_case(),
                          _as_chain->_is_registered,
                          false,
                          tdata->msg,
                          trail()))
  {
    LOG_DEBUG("No match for %s", to_string().c_str());
    return AsChainLink::Disposition::Next;
  }

  AsInvocation application_server = ifc.as_invocation();
  server_name = application_server.server_name;

  // Store the application server name in the AsInformation structure for this
  // link.
  _as_chain->_as_info[_index].as_uri = server_name;

  // Store the default handling as we may need it later.
  _default_handling = application_server.default_handling;

  return AsChainLink::Disposition::Skip;
}
Exemple #18
0
void pressKey(unsigned char key, int x, int y)
{
  int mod = glutGetModifiers();
  //only lowercase keys
  if(key<='Z' && key>='A')
    key=key-'A'+'a';
  //set pressed key
  pressed[key]=1;
  pressed_last=key;
  //quit on Ctrl+C
  if((key==3)&&(mod&2))
    exit(0);
  if(key==' ')
    g_stop_updating^=1;
  //print info on i
  if(key=='i')
  {
    printf("pos: %f, %f, %f\n",cam_pos.x,cam_pos.y,cam_pos.z);
    printf("dir: %f, %f, %f\n",cam_dir.x,cam_dir.y,cam_dir.z);
    printf("up: %f, %f, %f\n",cam_up.x,cam_up.y,cam_up.z);
    printf("side: %f, %f, %f\n",cam_side.x,cam_side.y,cam_side.z);
  }
  trail();
}
void BGCFSproutletTsx::on_rx_initial_request(pjsip_msg* req)
{
  // Create an ACR for this transaction.
  _acr = _bgcf->get_acr(trail());
  _acr->rx_request(req);

  std::vector<std::string> bgcf_routes;
  std::string routing_value;
  bool routing_with_number = false;
  PJUtils::update_request_uri_np_data(req,
                                      get_pool(req),
                                      _bgcf->_enum_service,
                                      _bgcf->_override_npdi,
                                      trail());
  pjsip_uri* req_uri = (pjsip_uri*)req->line.req.uri;
  URIClass uri_class = URIClassifier::classify_uri(req_uri);

  if (PJUtils::get_rn(req_uri, routing_value))
  {
    // Find the downstream routes based on the number.
    bgcf_routes = _bgcf->get_route_from_number(routing_value, trail());

    // If there are no matching routes, just route based on the domain - this
    // only matches any wild card routing set up
    if (bgcf_routes.empty())
    {
      routing_value = "";
      bgcf_routes = _bgcf->get_route_from_domain(routing_value, trail());
    }
    else
    {
      routing_with_number = true;
    }
  }
  else if ((uri_class == LOCAL_PHONE_NUMBER) ||
           (uri_class == GLOBAL_PHONE_NUMBER))
  {
    // Try to route based on the phone number first
    pj_str_t pj_user = PJUtils::user_from_uri(req_uri);
    routing_value = PJUtils::pj_str_to_string(&pj_user);
    bgcf_routes = _bgcf->get_route_from_number(routing_value, trail());

    // If there are no matching routes, just route based on the domain - this
    // only matches any wild card routing set up
    if (bgcf_routes.empty())
    {
      routing_value = "";
      bgcf_routes = _bgcf->get_route_from_domain(routing_value, trail());
    }
    else
    {
      routing_with_number = true;
    }
  }
  else
  {
    routing_value = PJUtils::pj_str_to_string(&((pjsip_sip_uri*)req_uri)->host);

    // Find the downstream routes based on the domain.
    bgcf_routes = _bgcf->get_route_from_domain(routing_value, trail());
  }

  if (!bgcf_routes.empty())
  {
    // The BGCF should be in control of what routes get added - delete existing
    // ones first.
    PJUtils::remove_hdr(req, &STR_ROUTE);

    for (std::vector<std::string>::iterator ii = bgcf_routes.begin();
         ii != bgcf_routes.end();
         ++ii)
    {
      pjsip_uri* route_uri = PJUtils::uri_from_string(*ii, get_pool(req), PJ_TRUE);
      route_uri = (route_uri == NULL) ? route_uri :
                                        (pjsip_uri*)pjsip_uri_get_uri(route_uri);

      if (route_uri != NULL && PJSIP_URI_SCHEME_IS_SIP(route_uri))
      {
        PJUtils::add_route_header(req, (pjsip_sip_uri*)route_uri, get_pool(req));
      }
      else
      {
        TRC_WARNING("Configured route (%s) isn't a valid SIP URI", (*ii).c_str());

        pjsip_msg* rsp = create_response(req, PJSIP_SC_INTERNAL_SERVER_ERROR);
        send_response(rsp);
        free_msg(req);

        return;
      }
    }

    send_request(req);
  }
  else
  {
    TRC_DEBUG("No route configured for %s", routing_value.c_str());

    if ((routing_value == "") || (routing_with_number))
    {
      // If the routing_value is blank we were trying to route a telephone number and
      // there are no more routes to try. If we had an rn value and this failed then
      // there are also no more routes to try.
      pjsip_msg* rsp = create_response(req,
                                       PJSIP_SC_NOT_FOUND,
                                       "No route to target");
      send_response(rsp);
      free_msg(req);
    }
    else
    {
      // Previous behaviour on no route was to try to forward the request as-is,
      // (so trying to route to the domain in the request URI directly).
      send_request(req);
    }
  }
}
 literal fresh() {
     return trail(m.mk_fresh_const("x", m.mk_bool_sort()));
 }
void SubscriptionSproutletTsx::process_subscription_request(pjsip_msg* req)
{
  SAS::TrailId trail_id = trail();

  // Get the URI from the To header and check it is a SIP or SIPS URI.
  pjsip_uri* uri = (pjsip_uri*)pjsip_uri_get_uri(PJSIP_MSG_TO_HDR(req)->uri);

  if ((!PJSIP_URI_SCHEME_IS_SIP(uri)) && (!PJSIP_URI_SCHEME_IS_TEL(uri)))
  {
    // Reject a non-SIP/TEL URI with 404 Not Found (RFC3261 isn't clear
    // whether 404 is the right status code - it says 404 should be used if
    // the AoR isn't valid for the domain in the RequestURI).
    TRC_DEBUG("Rejecting subscribe request using invalid URI scheme");

    SAS::Event event(trail_id, SASEvent::SUBSCRIBE_FAILED_EARLY_URLSCHEME, 0);
    SAS::report_event(event);

    pjsip_msg* rsp = create_response(req, PJSIP_SC_NOT_FOUND);
    send_response(rsp);
    free_msg(req);
    return;
  }

  // Check if the contact header is present. If it isn't, we want to abort
  // processing before going any further, to avoid unnecessary work.
  pjsip_contact_hdr* contact_hdr =
             (pjsip_contact_hdr*)pjsip_msg_find_hdr(req, PJSIP_H_CONTACT, NULL);

  if (contact_hdr == NULL)
  {
    TRC_DEBUG("Unable to parse contact header from request. "
              "Aborting processing");
    pjsip_msg* rsp = create_response(req, PJSIP_SC_BAD_REQUEST);
    send_response(rsp);
    free_msg(req);
    return;
  }

  // Check if this is a subscription request from a binding that was emergency
  // registered.
  bool emergency_subscription = false;

  while (contact_hdr != NULL)
  {
    emergency_subscription = PJUtils::is_emergency_registration(contact_hdr);

    if (!emergency_subscription)
    {
      break;
    }

    contact_hdr = (pjsip_contact_hdr*) pjsip_msg_find_hdr(req,
                                                          PJSIP_H_CONTACT,
                                                          contact_hdr->next);
  }

  if (emergency_subscription)
  {
    // Reject a subscription with a Contact header containing a contact address
    // that's been registered for emergency service.
    TRC_DEBUG("Rejecting subscribe request from emergency registration");

    SAS::Event event(trail_id, SASEvent::SUBSCRIBE_FAILED_EARLY_EMERGENCY, 0);
    SAS::report_event(event);

    // Allow-Events is a mandatory header on 489 responses.
    pjsip_msg* rsp = create_response(req, PJSIP_SC_BAD_EVENT);
    pjsip_generic_string_hdr* allow_events_hdr =
                           pjsip_generic_string_hdr_create(get_pool(rsp),
                                                           &STR_ALLOW_EVENTS,
                                                           &STR_REG);
    pjsip_msg_add_hdr(rsp, (pjsip_hdr*)allow_events_hdr);
    send_response(rsp);
    free_msg(req);
    return;
  }

  // At this point we are going to attempt to process the subscribe.
  // Canonicalize the public ID from the URI in the To header.
  std::string public_id = PJUtils::public_id_from_uri(uri);

  TRC_DEBUG("Process SUBSCRIBE for public ID %s", public_id.c_str());

  // Get the call identifier from the headers.
  std::string cid = PJUtils::pj_str_to_string(&PJSIP_MSG_CID_HDR(req)->id);

  // Add SAS markers to the trail attached to the message so the trail
  // becomes searchable.
  SAS::Event event(trail_id, SASEvent::SUBSCRIBE_START, 0);
  event.add_var_param(public_id);
  SAS::report_event(event);

  // Create an ACR for the request. The node role is always considered
  // originating for SUBSCRIBE requests.
  ACR* acr = _subscription->_acr_factory->get_acr(trail_id,
                                                  ACR::CALLING_PARTY,
                                                  ACR::NODE_ROLE_ORIGINATING);
  acr->rx_request(req);

  // Work out the expiry time of the subscription.
  pjsip_expires_hdr* expires =
             (pjsip_expires_hdr*)pjsip_msg_find_hdr(req, PJSIP_H_EXPIRES, NULL);
  int expiry = (expires != NULL) ?
                expires->ivalue :
                SubscriptionSproutlet::DEFAULT_SUBSCRIPTION_EXPIRES;

  if (expiry > _subscription->_max_expires)
  {
    // Expiry is too long, set it to the maximum.
    TRC_DEBUG("Requested expiry (%d) is too long, setting to the maximum (%d)",
              expiry, _subscription->_max_expires);
    expiry = _subscription->_max_expires;
  }

  // Create a subscription object from the request that we can pass down to
  // be set into/updated in the different stores
  Subscription* new_subscription = create_subscription(req, expiry);
  HSSConnection::irs_info irs_info;
  HTTPCode rc;

  // Update or remove the subscription in the subscriber manager depending on
  // the expiry time.
  if (expiry != 0)
  {
    TRC_DEBUG("Adding/updating the subscription with ID %s",
              new_subscription->get_id().c_str());

    Subscriptions new_subscriptions;
    new_subscriptions.insert(std::make_pair(new_subscription->get_id(), new_subscription));
    rc = _subscription->_sm->update_subscriptions(
                   public_id,
                   new_subscriptions,
                   irs_info,
                   trail_id);
  }
  else
  {
    TRC_DEBUG("Removing the subscription with ID %s",
              new_subscription->get_id().c_str());

    rc = _subscription->_sm->remove_subscriptions(public_id,
                                                  {new_subscription->get_id()},
                                                  irs_info,
                                                  trail_id);
  }

  pjsip_status_code st_code =
                 determine_sm_sip_response(rc, irs_info._regstate, "SUBSCRIBE");

  pjsip_msg* rsp = create_response(req, st_code);

  if (st_code == PJSIP_SC_OK)
  {
    // The subscribe was successful. SAS log, and add headers to the response.
    TRC_DEBUG("The subscribe has been successful");

    SAS::Event sub_accepted(trail_id, SASEvent::SUBSCRIBE_ACCEPTED, 0);
    SAS::report_event(sub_accepted);

    // Add expires headers
    pjsip_expires_hdr* expires_hdr = pjsip_expires_hdr_create(get_pool(rsp),
                                                              expiry);
    pjsip_msg_add_hdr(rsp, (pjsip_hdr*)expires_hdr);

    // Add the contact header
    pjsip_contact_hdr* contact_hdr = pjsip_contact_hdr_create(get_pool(rsp));
    pjsip_name_addr* contact_uri = pjsip_name_addr_create(get_pool(rsp));
    contact_uri->uri = (pjsip_uri*)stack_data.scscf_uri;
    contact_hdr->uri = (pjsip_uri*)contact_uri;
    pjsip_msg_add_hdr(rsp, (pjsip_hdr*)contact_hdr);

    // Add a P-Charging-Function-Addresses header to the successful SUBSCRIBE
    // response containing the charging addresses returned by the HSS.
    PJUtils::add_pcfa_header(rsp,
                             get_pool(rsp),
                             irs_info._ccfs,
                             irs_info._ecfs,
                             false);

  }
  else if (st_code == PJSIP_SC_TEMPORARILY_UNAVAILABLE)
  {
    // A 480 response means that the subscriber wasn't registered. SAS log
    // this.
    TRC_DEBUG("The subscribe has failed as the subscriber (%s) wasn't registered",
              public_id.c_str());

    SAS::Event event(trail_id, SASEvent::SUBSCRIBE_FAILED_EARLY_NOT_REG, 0);
    SAS::report_event(event);
  }
  else
  {
    // The subscribe was unsuccessful.
    TRC_DEBUG("The subscribe failed with return code %d", st_code);

    SAS::Event sub_failed(trail_id, SASEvent::SUBSCRIBE_FAILED, 0);
    sub_failed.add_var_param(public_id);
    SAS::report_event(sub_failed);
  }

  // Add the to tag to the response (even if the subscribe was rejected).
  pjsip_to_hdr *to = (pjsip_to_hdr*) pjsip_msg_find_hdr(rsp,
                                                        PJSIP_H_TO,
                                                        NULL);
  pj_strdup2(get_pool(rsp), &to->tag, new_subscription->_to_tag.c_str());

  // Pass the response to the ACR.
  acr->tx_response(rsp);

  // Send the response.
  send_response(rsp);

  // Send the ACR and delete it.
  acr->send();
  delete acr; acr = NULL;

  delete new_subscription; new_subscription = NULL;
  free_msg(req);
}
 literal mk_min(literal a, literal b) { return trail(m.mk_and(a, b)); }
 literal mk_not(literal a) { if (m.is_not(a,a)) return a;
     return trail(m.mk_not(a));
 }
void ICSCFSproutletTsx::on_rx_initial_request(pjsip_msg* req)
{
  pj_pool_t* pool = get_pool(req);

  pjsip_route_hdr* hroute = (pjsip_route_hdr*)
                                pjsip_msg_find_hdr(req, PJSIP_H_ROUTE, NULL);

  // TS 24.229 says I-CSCF processing shouldn't be done if a message has more than one Route header.
  // We've stripped one off in Sproutlet processing, so check for a second and just forward the
  // message if it's there.
  if (hroute != NULL)
  {
    send_request(req);
    return;
  }

  pjsip_uri* next_hop = PJUtils::next_hop(req);
  URIClass next_hop_class = URIClassifier::classify_uri(next_hop);
  if (req->line.req.method.id == PJSIP_ACK_METHOD &&
      next_hop == req->line.req.uri &&
      ((next_hop_class == NODE_LOCAL_SIP_URI) ||
       (next_hop_class == HOME_DOMAIN_SIP_URI)))
  {
    // Ignore ACK messages with no Route headers and a local Request-URI, as:
    // - the I-CSCF should not be handling these
    // - we've seen ACKs matching this descrption being generated at overload and looping repeatedly
    //
    // This is a fairly targeted fix for https://github.com/Metaswitch/sprout/issues/1091.
    // TODO: remove this code when #1091 is fixed by other means.
    free_msg(req);
    return;
  }

  // Create an ACR for this transaction.
  _acr = _icscf->get_acr(trail());
  _acr->rx_request(req);

  TRC_DEBUG("I-CSCF initialize transaction for non-REGISTER request");

  // Before we clone the request for retries, remove the P-Profile-Key header
  // if present.
  PJUtils::remove_hdr(req, &STR_P_PROFILE_KEY);

  // Determine orig/term and the served user's name.
  const pjsip_route_hdr* route = route_hdr();
  std::string impu;

  if ((route != NULL) &&
      (pjsip_param_find(&((pjsip_sip_uri*)route->name_addr.uri)->other_param,
                        &STR_ORIG) != NULL))
  {
    // Originating request.
    TRC_DEBUG("Originating request");
    _originating = true;
    impu = PJUtils::public_id_from_uri(PJUtils::orig_served_user(req));

    SAS::Event event(trail(), SASEvent::ICSCF_RCVD_ORIG_NON_REG, 0);
    event.add_var_param(impu);
    event.add_var_param(req->line.req.method.name.slen,
                        req->line.req.method.name.ptr);
    SAS::report_event(event);
  }
  else
  {
    // Terminating request.
    TRC_DEBUG("Terminating request");
    _originating = false;
    pjsip_uri* uri = PJUtils::term_served_user(req);

    // If the Req URI is a SIP URI with the user=phone parameter set, is not a
    // GRUU and the user part starts with '+' (i.e. is a global phone number),
    // we should replace it with a tel URI, as per TS24.229 5.3.2.1.
    if (PJSIP_URI_SCHEME_IS_SIP(uri))
    {
      URIClass uri_class = URIClassifier::classify_uri(uri);
      pjsip_sip_uri* sip_uri = (pjsip_sip_uri*)uri;

      if (uri_class == GLOBAL_PHONE_NUMBER)
      {
        TRC_DEBUG("Change request URI from SIP URI to tel URI");
        req->line.req.uri =
          PJUtils::translate_sip_uri_to_tel_uri(sip_uri, pool);
      }
    }

    impu = PJUtils::public_id_from_uri(PJUtils::term_served_user(req));

    SAS::Event event(trail(), SASEvent::ICSCF_RCVD_TERM_NON_REG, 0);
    event.add_var_param(impu);
    event.add_var_param(req->line.req.method.name.slen,
                        req->line.req.method.name.ptr);
    SAS::report_event(event);
  }

  // Create an LIR router to handle the HSS interactions and S-CSCF
  // selection.
  _router = (ICSCFRouter*)new ICSCFLIRouter(_icscf->get_hss_connection(),
                                            _icscf->get_scscf_selector(),
                                            trail(),
                                            _acr,
                                            _icscf->port(),
                                            impu,
                                            _originating);

  pjsip_sip_uri* scscf_sip_uri = NULL;

  // Use the router we just created to query the HSS for an S-CSCF to use.
  // TS 32.260 Table 5.2.1.1 says an EVENT ACR should be generated on the
  // completion of a Cx query issued in response to a SIP INVITE
  bool do_billing = (req->line.req.method.id == PJSIP_INVITE_METHOD);
  std::string wildcard;
  pjsip_status_code status_code =
    (pjsip_status_code)_router->get_scscf(pool,
                                          scscf_sip_uri,
                                          wildcard,
                                          do_billing);

  if ((!_originating) && (scscf_not_found(status_code)))
  {
    TRC_DEBUG("Couldn't find an S-CSCF, attempt to translate the URI");
    pjsip_uri* uri = PJUtils::term_served_user(req);
    URIClass uri_class = URIClassifier::classify_uri(uri, false);

    // For terminating processing, if the HSS indicates that the user does not
    // exist, and if the request URI is a tel URI, try an ENUM translation. If
    // this succeeds, go back to the HSS. See TS24.229, 5.3.2.1.
    //
    // Before doing that we should check whether the enforce_user_phone flag is
    // set. If it isn't, and we have a numeric SIP URI, it is possible that
    // this should have been a tel URI, so translate it and do the HSS lookup
    // again.  Once again, only do this for global numbers.
    if (PJSIP_URI_SCHEME_IS_SIP(uri) && (uri_class == GLOBAL_PHONE_NUMBER))
    {
      TRC_DEBUG("enforce_user_phone set to false, try using a tel URI");
      uri = PJUtils::translate_sip_uri_to_tel_uri((pjsip_sip_uri*)uri, pool);
      req->line.req.uri = uri;

      // We need to change the IMPU stored on our LIR router so that when
      // we do a new LIR we look up the new IMPU.
      impu = PJUtils::public_id_from_uri(PJUtils::term_served_user(req));
      ((ICSCFLIRouter *)_router)->change_impu(impu);
      status_code = (pjsip_status_code)_router->get_scscf(pool,
                                                          scscf_sip_uri,
                                                          wildcard,
                                                          do_billing);
    }

    if (_icscf->_enum_service)
    {
      // If we still haven't found an S-CSCF, we can now try an ENUM lookup.
      // We put this processing in a loop because in theory we may go round
      // several times before finding an S-CSCF. In reality this is unlikely
      // so we set MAX_ENUM_LOOKUPS to 2.
      for (int ii = 0;
           (ii < MAX_ENUM_LOOKUPS) && (scscf_not_found(status_code));
           ++ii)
      {
        if (PJSIP_URI_SCHEME_IS_TEL(uri))
        {
          // Do an ENUM lookup and see if we should translate the TEL URI
          pjsip_uri* original_req_uri = req->line.req.uri;
          _icscf->translate_request_uri(req, get_pool(req), trail());
          uri = req->line.req.uri;
          URIClass uri_class = URIClassifier::classify_uri(uri, false, true);

          std::string rn;

          if ((uri_class == NP_DATA) ||
              (uri_class == FINAL_NP_DATA))
          {
            // We got number portability information from ENUM - drop out and route to the BGCF.
            route_to_bgcf(req);
            return;
          }
          else if (pjsip_uri_cmp(PJSIP_URI_IN_REQ_URI,
                                 original_req_uri,
                                 req->line.req.uri) != PJ_SUCCESS)
          {
            // The URI has changed, so make sure we do a LIR lookup on it.
            impu = PJUtils::public_id_from_uri(req->line.req.uri);
            ((ICSCFLIRouter *)_router)->change_impu(impu);
          }

          // If we successfully translate the req URI and end up with either another TEL URI or a
          // local SIP URI, we should look for an S-CSCF again.
          if ((uri_class == LOCAL_PHONE_NUMBER) ||
              (uri_class == GLOBAL_PHONE_NUMBER) ||
              (uri_class == HOME_DOMAIN_SIP_URI))
          {
            // TEL or local SIP URI.  Look up the S-CSCF again.
            status_code = (pjsip_status_code)_router->get_scscf(pool,
                                                                scscf_sip_uri,
                                                                wildcard,
                                                                do_billing);
          }
          else
          {
            // Number translated to off-switch.  Drop out of the loop.
            ii = MAX_ENUM_LOOKUPS;
          }
        }
        else
        {
          // Can't translate the number, skip to the end of the loop.
          ii = MAX_ENUM_LOOKUPS;
        }
      }
    }
    else
    {
      // The user is not in the HSS and ENUM is not configured. TS 24.229
      // says that, as an alternative to ENUM, we can "forward the request to
      // the transit functionality for subsequent routeing". Let's do that
      // (currently, we assume the BGCF is the transit functionality, but that
      // may be made configurable in future).
      TRC_DEBUG("No ENUM service available - outing request directly to transit function (BGCF)");
      route_to_bgcf(req);
      return;
    }
  }

  URIClass uri_class = URIClassifier::classify_uri(req->line.req.uri);
  if (status_code == PJSIP_SC_OK)
  {
    TRC_DEBUG("Found SCSCF for non-REGISTER");

    if (_originating)
    {
      // Add the `orig` parameter.
      pjsip_param* orig_param = PJ_POOL_ALLOC_T(get_pool(req), pjsip_param);
      pj_strdup(get_pool(req), &orig_param->name, &STR_ORIG);
      orig_param->value.slen = 0;
      pj_list_insert_after(&scscf_sip_uri->other_param, orig_param);
    }

    // Add the P-Profile-Key header here if we've got a wildcard
    if (wildcard != "")
    {
      add_p_profile_header(wildcard, req);
    }

    PJUtils::add_route_header(req, scscf_sip_uri, get_pool(req));
    send_request(req);
  }
  else if ((uri_class == OFFNET_SIP_URI) ||
           (uri_class == GLOBAL_PHONE_NUMBER))
  {
    // Target is a TEL URI or not in our home domain.  Pass to the BGCF.
    route_to_bgcf(req);
  }
  else
  {
    // Target is in our home domain, but we failed to find an S-CSCF. This is the final response.
    pjsip_msg* rsp = create_response(req, status_code);
    send_response(rsp);
    free_msg(req);
  }
}
 literal mk_max(literal a, literal b) {
     return trail(m.mk_or(a, b));
 }
Exemple #26
0
HTTPCode AuthTimeoutHandler::handle_response(std::string body)
{
  Json::Value json_body;
  std::string json_str = body;
  Json::Reader reader;
  bool parsingSuccessful = reader.parse(json_str.c_str(), json_body);

  if (!parsingSuccessful)
  {
    LOG_ERROR("Failed to read opaque data, %s",
              reader.getFormattedErrorMessages().c_str());
    return HTTP_BAD_RESULT;
  }

  if ((json_body.isMember("impi")) &&
      ((json_body)["impi"].isString()))
  {
    _impi = json_body.get("impi", "").asString();
  }
  else
  {
    LOG_ERROR("IMPI not available in JSON");
    return HTTP_BAD_RESULT;
  }

  if ((json_body.isMember("impu")) &&
      ((json_body)["impu"].isString()))
  {
    _impu = json_body.get("impu", "").asString();
  }
  else
  {
    LOG_ERROR("IMPU not available in JSON");
    return HTTP_BAD_RESULT;
  }

  if ((json_body.isMember("nonce")) &&
      ((json_body)["nonce"].isString()))
  {
    _nonce = json_body.get("nonce", "").asString();
  }
  else
  {
    LOG_ERROR("Nonce not available in JSON");
    return HTTP_BAD_RESULT;
  }

  Json::Value* json = _cfg->_avstore->get_av(_impi, _nonce, trail());
  bool success = false;


  if (json == NULL)
  {
    // Mainline case - our AV has already been deleted because the
    // user has tried to authenticate. No need to notify the HSS in
    // this case (as they'll either have successfully authenticated
    // and triggered a REGISTRATION SAR, or failed and triggered an
    // AUTHENTICATION_FAILURE SAR).
    success = true;
  }
  else
  {
    LOG_DEBUG("AV for %s:%s has timed out", _impi.c_str(), _nonce.c_str());

    // Note that both AV deletion and the AUTHENTICATION_TIMEOUT SAR
    // are idempotent, so there's no problem if Chronos' timer pops
    // twice (e.g. if we have high latency and these operations take
    // more than 2 seconds).

    // If either of these operations fail, we return a 500 Internal
    // Server Error - this will trigger Chronos to try a different
    // Sprout, which may have better connectivity to Homestead or Memcached.
    success = _cfg->_hss->update_registration_state(_impu, _impi, HSSConnection::AUTH_TIMEOUT, 0);

    if (success)
    {
      success = _cfg->_avstore->delete_av(_impi, _nonce, trail());
    }

    delete json;
  }
  return success ? HTTP_OK : HTTP_SERVER_ERROR;
}
Exemple #27
0
RegStore::AoR* DeregistrationHandler::set_aor_data(RegStore* current_store,
                                                   std::string aor_id,
                                                   std::string private_id,
                                                   RegStore::AoR* previous_aor_data,
                                                   RegStore* remote_store,
                                                   bool is_primary)
{
  RegStore::AoR* aor_data = NULL;
  bool previous_aor_data_alloced = false;
  bool all_bindings_expired = false;

  do
  {
    if (!reg_store_access_common(&aor_data, previous_aor_data_alloced, aor_id,
                                 current_store, remote_store, &previous_aor_data, trail()))
    {
      // LCOV_EXCL_START - local store (used in testing) never fails
      break;
      // LCOV_EXCL_STOP
    }

    std::vector<std::string> binding_ids;

    for (RegStore::AoR::Bindings::const_iterator i = aor_data->bindings().begin();
         i != aor_data->bindings().end();
         ++i)
    {
      // Get a list of the bindings to iterate over
      binding_ids.push_back(i->first);
    }

    for (std::vector<std::string>::const_iterator i = binding_ids.begin();
         i != binding_ids.end();
         ++i)
    {
      std::string b_id = *i;
      RegStore::AoR::Binding* b = aor_data->get_binding(b_id);

      if (private_id == "" || private_id == b->_private_id)
      {
        // Update the cseq
        aor_data->_notify_cseq++;

        // The binding matches the private id, or no private id was supplied.
        // Send a SIP NOTIFY for this binding if there are any subscriptions
        if (_notify == "true" && is_primary)
        {
          for (RegStore::AoR::Subscriptions::const_iterator j = aor_data->subscriptions().begin();
              j != aor_data->subscriptions().end();
               ++j)
          {
            // LCOV_EXCL_START
            current_store->send_notify(j->second, aor_data->_notify_cseq, b, b_id);
            // LCOV_EXCL_STOP
          }
        }

        aor_data->remove_binding(b_id);
      }
    }
  }
  while (!current_store->set_aor_data(aor_id, aor_data, is_primary, trail(), all_bindings_expired));

  if (private_id == "")
  {
    // Deregister with any application servers
    std::vector<std::string> uris;
    std::map<std::string, Ifcs> ifc_map;
    std::string state;
    LOG_INFO("ID %s", aor_id.c_str());
    _cfg->_hss->get_registration_data(aor_id, state, ifc_map, uris, 0);
    RegistrationUtils::deregister_with_application_servers(ifc_map[aor_id], current_store, aor_id, 0);
  }

  // If we allocated the AoR, tidy up.
  if (previous_aor_data_alloced)
  {
    delete previous_aor_data;
  }

  return aor_data;
}
void ICSCFSproutletTsx::on_rx_response(pjsip_msg* rsp, int fork_id)
{
  if (_acr != NULL)
  {
    // Pass the received response to the ACR.
    // @TODO - timestamp from response???
    _acr->rx_response(rsp);
  }

  // Check if this response is one that we are allowed to retry the HSS lookup
  // for.  See TS 24.229 - section 5.3.2.2.
  //
  // Note we support service restoration, so integrity-protected settings in
  // Authorization header are immaterial.
  //
  // Note also that we can never retry once we've routed to the BGCF.
  pjsip_status_code rsp_status = (pjsip_status_code)rsp->line.status.code;
  const ForkState& fork_status = fork_state(fork_id);
  TRC_DEBUG("Check retry conditions for non-REGISTER, S-CSCF %sresponsive",
            (fork_status.error_state != NONE) ? "not " : "");
  if ((!_routed_to_bgcf) &&
      (fork_status.error_state != NONE))
  {
    // Indeed it it, first log to SAS.
    TRC_DEBUG("Attempt retry to alternate S-CSCF for non-REGISTER request");
    std::string st_code = std::to_string(rsp_status);
    SAS::Event event(trail(), SASEvent::SCSCF_RETRY, 0);
    std::string method = "non-REGISTER";
    event.add_var_param(method);
    event.add_var_param(st_code);
    SAS::report_event(event);

    // Now we can simply reuse the UA router we made on the initial request.
    pjsip_sip_uri* scscf_sip_uri = NULL;
    pjsip_msg* req = original_request();
    pj_pool_t* pool = get_pool(req);

    // TS 32.260 Table 5.2.1.1 says an EVENT ACR should be generated on the
    // completion of a Cx query issued in response to a SIP INVITE. It's
    // ambiguous on whether this should be sent on each Cx query completion
    // so we err on the side of over-sending events.
    bool do_billing = (rsp->line.req.method.id == PJSIP_INVITE_METHOD);
    std::string wildcard;
    int status_code = _router->get_scscf(pool,
                                         scscf_sip_uri,
                                         wildcard,
                                         do_billing);

    if (status_code == PJSIP_SC_OK)
    {
      TRC_DEBUG("Found SCSCF for non-REGISTER");

      if (_originating)
      {
        // Add the `orig` parameter.
        pjsip_param* orig_param = PJ_POOL_ALLOC_T(pool, pjsip_param);
        pj_strdup(pool, &orig_param->name, &STR_ORIG);
        orig_param->value.slen = 0;
        pj_list_insert_after(&scscf_sip_uri->other_param, orig_param);
      }

      // Add the P-Profile-Key header here if we've got a wildcard
      if (wildcard != "")
      {
        add_p_profile_header(wildcard, req);
      }

      PJUtils::add_route_header(req, scscf_sip_uri, pool);
      send_request(req);

      // We're not forwarding this response upstream.
      free_msg(rsp);
    }
    else
    {
      free_msg(req);
      send_response(rsp);
    }
  }
  else
  {
    // Provisional, successful or non-retryable response, simply forward on
    // upstream.
    send_response(rsp);
  }
}
    bool mk_interp_tail_simplifier::propagate_variable_equivalences(rule * r, rule_ref& res) {
        if (!m_context.get_params ().xform_tail_simplifier_pve ())
            return false;
        unsigned u_len = r->get_uninterpreted_tail_size();
        unsigned len = r->get_tail_size();
        if (u_len == len) {
            return false;
        }

        m_todo.reset();
        m_leqs.reset();
        for (unsigned i = u_len; i < len; i++) {
            m_todo.push_back(r->get_tail(i));
            SASSERT(!r->is_neg_tail(i));
        }

        m_rule_subst.reset(r);

        expr_ref_vector trail(m);
        expr_ref tmp1(m), tmp2(m);
        bool found_something = false;

#define TRY_UNIFY(_x,_y) if (m_rule_subst.unify(_x,_y)) { found_something = true; }
#define IS_FLEX(_x) (is_var(_x) || m.is_value(_x))

        while (!m_todo.empty()) {
            expr * arg1, *arg2;
            expr * t0 = m_todo.back();
            m_todo.pop_back();
            expr* t = t0;
            bool neg = m.is_not(t, t);
            if (is_var(t)) {
                TRY_UNIFY(t, neg ? m.mk_false() : m.mk_true());
            }
            else if (!neg && m.is_and(t)) {
                app* a = to_app(t);
                m_todo.append(a->get_num_args(), a->get_args());
            }
            else if (!neg && m.is_eq(t, arg1, arg2) && IS_FLEX(arg1) && IS_FLEX(arg2)) {
                TRY_UNIFY(arg1, arg2);
            }
            else if (m.is_iff(t, arg1, arg2)) {
                //determine the polarity of the equivalence and remove the negations
                while (m.is_not(arg1, arg1)) neg = !neg;
                while (m.is_not(arg2, arg2)) neg = !neg;
                if (!is_var(arg1)) {
                    std::swap(arg1, arg2);
                }
                if (!IS_FLEX(arg1) || !IS_FLEX(arg2)) {
                    // no-op
                }
                else if (is_var(arg1) && !neg) {
                    TRY_UNIFY(arg1, arg2);
                }
                else if (is_var(arg1) && neg && m.is_true(arg2)) {
                    TRY_UNIFY(arg1, m.mk_false());
                }
                else if (is_var(arg1) && neg && m.is_false(arg2)) {
                    TRY_UNIFY(arg1, m.mk_true());
                }
            }
            else if (!neg && (a.is_le(t, arg1, arg2) || a.is_ge(t, arg2, arg1))) {
                tmp1 = a.mk_sub(arg1, arg2);
                tmp2 = a.mk_sub(arg2, arg1);
                if (false && m_leqs.contains(tmp2) && IS_FLEX(arg1) && IS_FLEX(arg2)) {
                    TRY_UNIFY(arg1, arg2);
                }
                else {
                    trail.push_back(tmp1);
                    m_leqs.insert(tmp1);
                }
            }
        }

        if (!found_something) {
            return false;
        }
        TRACE("dl_interp_tail_simplifier_propagation_pre",
                tout << "will propagate rule:\n";
                r->display(m_context, tout);
            );
Exemple #30
0
main(int argc , char *argv[])
{
inpfname = argv[1];
int runno, itno, antno;
double time_used;


read_data(inpfname);
print_data();

init_out(inpfname);


time_used = elapsed_time( VIRTUAL );
printf("Initialization took %.10f seconds\n",time_used);

for(runno=0;runno<runs;runno++)
{
seed = (long int ) time(NULL);
 start_timers();

 initialize_ants_variables(runno);


 initialize_trail();

 for(itno=0;  bestant.ofn != 436.00 &&  itno<ncmax ;itno++)
 {
	 
 iteration_init(itno);
  
 find_values();
  
 analysis( itno);
 

update_stats(itno,runno);

#if (usels == 1)

if(lswithitbest ==1)
{
ls(&itbestval,itno);
lsstats(itno,runno);
}

if(lswithbest ==1)
{
ls(&bestval,itno);
lsstats(itno,runno);
}

#endif

 trail();

if(!(itno%statsafterit))
{ print_itstats(itno ,runno);}

}//end of nc max iterations

update_stats(itno,runno);
report_run(runno);

}//end of runs

final_stats();

freememory();


}//end of main