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

📄 sipua.c

📁 未改进的经典的SIP NETWORK API。 请尽快给下载权限
💻 C
📖 第 1 页 / 共 3 页
字号:
  sip_status_t sip_rc;
  sip_msg_error_t error;

  sip_msg_body_t     * sdp_body = 0;
  sdp_announcement_t * sdp;
  
  char hostname[50];

  gethostname(hostname, 50);

  calling_uri = sip_msg_new_sip_url("user",
                                    hostname,
                                    port,
                                    NULL,
                                    NULL,
                                    SIP_MSG_NONE,
                                    NULL,
                                    -1,
                                    NULL,
                                    SIP_FALSE,
                                    NULL,
                                    NULL);
  if(!calling_uri) {
    sip_call_delete_instance(sip_ch_inst);
    printf("Unable to build the calling uri");
    return(1);
  }

  if(interactive) {
    printf("Press enter to start the call...\n");
    getchar();
  }

  from = sip_msg_new_from_header(calling_uri, NULL, NULL, NULL, NULL);
  if(!from) {
    printf("Unable to build the From: header\n");
    return(1);
  }

  contact = sip_msg_new_contact_header(calling_uri, NULL, -1, -1, NULL, NULL);
  if(!contact) {
    sip_call_delete_instance(sip_ch_inst);
    printf("Unable to build the Contact: header\n");
    return(1);
  }
  
  request_uri = sip_msg_parse_uri(sip_called_uri, &error);
  if(!request_uri) {
    printf("Syntax error near token '%s' in request URI\n",
           error.unexpected_token);
    return(1);
  }
  
  to = sip_msg_new_to_header(request_uri, NULL, NULL, NULL, NULL);
  if(!to) {
    printf("Unable to build the To: header\n");
    return(1);
  }
  
  call = SIP_CALL_NO_CALL;
  dialog = SIP_CALL_NO_DIALOG;
  transaction = SIP_CALL_NO_TRANSACTION;
  
  if(do_body) {

    sdp = sdp_new_announcement(0, 
                               "media", 
                               "user1", 
                               "12341234", 
                               "2",
                               "IN",
                               "IP4",
                               "127.0.0.2",
                               NULL);
    
    if(!sdp) {
      printf("Unable to build SDP announcement\n");
      exit(1);
    }
    
    sdp_body = sip_msg_new_sdp_body(sdp,
                                    SIP_FALSE, NULL);
  }

  if(!subscribe_event_name) {
    /* Normal INVITE case */

    sip_rc = sip_call_initiate(sip_ch_inst,
			       &call,
			       &dialog,
			       &transaction,
			       request_uri,
			       from,
			       to,
			       contact,
			       NULL,
			       sdp_body,
			       NULL);

    if(sip_rc != SIP_NORMAL) {
      printf("Error %d returned from sip_call_initiate\n", sip_rc);
      return(1);
    } else {
      printf("Initiate call ongoing...\n");
    }
  } else {
    /* SUBSCRIBE case */

    sip_msg_header_t * event;
    sip_subs_t subscription_id;

    event = sip_msg_new_event_header
      (subscribe_event_name, NULL, NULL, NULL);

    if(!event) {
      printf("Error returned from sip_msg_new_event_header\n");
      return 1;
    }

    sip_rc = sip_call_evt_subscribe
      (sip_ch_inst,
       &call,
       &dialog,
       &transaction,
       &subscription_id,
       request_uri,
       from,
       to,
       contact,
       event,
       NULL, /* expires header */
       NULL,
       sdp_body,
       NULL);

    if(sip_rc != SIP_NORMAL) {
      printf("Error %d returned from sip_call_evt_subscribe\n", sip_rc);
      return(1);
    } else {
      printf("SUBSCRIBE sent...\n");
    }
  }
    
  sip_msg_free_uri(calling_uri);
  sip_msg_free_uri(request_uri);
  sip_msg_free_header(from);
  sip_msg_free_header(to);
  sip_msg_free_header(contact);

  if(do_body) {
    sip_msg_free_body(sdp_body);
  }

  if(cancel_delay) {

    sip_trans_t new_trans;

    sleep(cancel_delay);
    
    printf("Releasing the call with a CANCEL or a BYE\n");

    /* send a CANCEL request */
    sip_call_release(sip_ch_inst,
		     call,
		     dialog,
		     &new_trans,
		     NULL,
		     NULL,
		     SIP_CALL_RELEASE_AUTOMATIC,
                     NULL);
  }

  return(0);
}

/*
 * FACILITY:
 *
 *      usage
 *
 * ABSTRACT:
 *
 *      The help string displayed in case of error when
 *      parsing the comand line.
 *
 * FORMAL PARAMETERS:
 *
 *      The name of the command (argv[0]).
 *
 * RETURN VALUE:
 *
 *      None
 *
 */

void usage(char * command_name, char * local_ip) 
{
  printf("\n%s [-c request_URI]"
         "\n"
         "\n  Starts a SIP UAS on the specified port, and an optional UAC"
         "\n  initiating a call (with the -c option)."
         "\n"
         "\n   -p port       : The -p option specifies the UDP port number"
         "\n                   for the proxy server. The default port is 5060."
         "\n"
         "\n   -c Req_URI    : The -c option sends an INVITE request"
         "\n                   to the specified URI, and manage the call"
         "\n                   as a UAC. You can use the URI syntax to"
         "\n                   set the destination port number (e.g."
         "\n                   sip:user@%s:6060). 3 seconds after"
         "\n                   call establishment, this option sends a"
         "\n                   BYE request to terminate the call."
         "\n"
         "\n   -cc delay     : Modifier for the -c option. This option"
         "\n                   sends a CANCEL request 'delay' seconds after"
         "\n                   the INVITE request, if and only if a 1xx" 
         "\n                   response has been recieved."
         "\n"
         "\n   -cb           : Modifier for the -c option. This option"
         "\n                   remove the BYE transaction after call"
         "\n                   establishment. The call is leaved opened" 
         "\n                   once established."
         "\n"
         "\n   -cs event     : Modifier for the -c option. Sends a SUBSCRIBE"
	 "\n                   request (with the given event name) instead the"
	 "\n                   normal INVITE request."
         "\n"
         "\n   -us nb        : Modifier for the -cs option: Unsubscribe after"
	 "\n                   nb NOTIFY have been reveived."
         "\n"
         "\n   -b delay      : When UAS, send a BYE 'delay' seconds after"
         "\n                   call establishment."
         "\n"
         "\n   -d delay      : When UAS, wait for 'delay' seconds before"
         "\n                   answering an INVITE request."
         "\n"
         "\n   -nd           : When UAS, do not wait before accepting calls."
         "\n"
         "\n   -ne           : Do not exit when the first call is finished."
         "\n"
         "\n   -i            : Interactive mode."
         "\n"
         "\n   -h            : Displays this help screen."
         "\n"
         "\n   -bd           : Insert fake SDP body in INVITE request."
         "\n"
         "\n",
         command_name,
         local_ip);
}

/*
 * FACILITY:
 *
 *      main
 *
 * ABSTRACT:
 *
 *      The main entry of the process
 *
 * FORMAL PARAMETERS:
 *
 *      argc, argv command line parameters
 *
 * RETURN VALUE:
 *
 *      None
 *
 */

int main(int argc, char *argv[])
{
  sip_status_t                 sip_status = SIP_NORMAL;
  sip_trp_info_t               sip_trp_info[1];
  sip_uint32_t                 sip_nb_trp = 1;
  sip_call_callback_vector_t   sip_ch_callback;
  sip_call_inst_t              sip_ch_inst;
  sip_uint32_t                 sip_remaining_indic = 0;
  struct hostent             * sip_local_host = NULL;
  char                         hostname[80] = { 0 };
  int                          sip_port = 5060;
  char                       * sip_called_uri = NULL;
  char                         sip_local_ip[50];
  char                         sip_pid[16] = { 0 };
  sip_bool_t                   do_body = SIP_FALSE;
  sigset_t                     sig_set;
  int                          argi;

  /* Mask the SIPPIPE signal */
  sigemptyset(&sig_set);
  sigaddset(&sig_set, SIGPIPE);
  pthread_sigmask( SIG_BLOCK, &sig_set, 0 );

  if  ((gethostname(hostname,64) != 0)
   || (!(sip_local_host = gethostbyname(hostname))))
  {
    printf("cannot get local host informations\n");
    exit(1);
  }

  strcpy(sip_local_ip,
	 (char *) inet_ntoa
	 (*(struct in_addr *)(sip_local_host->h_addr_list[0])));

  for(argi = 1; argi < argc; argi++) {
    
    if(!strcmp(argv[argi], "-p")) {
      if((++argi) < argc) {
        sip_port = atol(argv[argi]);
      } else {
        usage(argv[0],sip_local_ip);
        exit(1);
      }
    }
    
    if((!strcmp(argv[argi], "-h"    )) ||
       (!strcmp(argv[argi], "--h"   )) || 
       (!strcmp(argv[argi], "--help")) || 
       (!strcmp(argv[argi], "-help" ))    ) {
      usage(argv[0],sip_local_ip);
      exit(0);
    }
    
    if(!strcmp(argv[argi], "-i")) {
      interactive = SIP_TRUE;
    }

    if(!strcmp(argv[argi], "-bd")) {
      do_body = SIP_TRUE;
    }

    if(!strcmp(argv[argi], "-cb")) {
      no_bye = SIP_TRUE;
    }

    if(!strcmp(argv[argi], "-nd")) {
      no_delay = SIP_TRUE;
    }

    if(!strcmp(argv[argi], "-ne")) {
      auto_exit = SIP_FALSE;
    }

    if(!strcmp(argv[argi], "-c")) {
      if((++argi) < argc) {
        sip_called_uri = argv[argi];
      } else {
        usage(argv[0],sip_local_ip);
        exit(1);
      }
    }

    if(!strcmp(argv[argi], "-cc")) {
      if((++argi) < argc) {
        cancel_delay = atol(argv[argi]);
      } else {
        usage(argv[0],sip_local_ip);
        exit(1);
      }
    }

    if(!strcmp(argv[argi], "-cs")) {
      if((++argi) < argc) {
        subscribe_event_name = argv[argi];
      } else {
        usage(argv[0],sip_local_ip);
        exit(1);
      }
    }

    if(!strcmp(argv[argi], "-b")) {
      if((++argi) < argc) {
        uas_bye_delay = atol(argv[argi]);
      } else {
        usage(argv[0],sip_local_ip);
        exit(1);
      }
    }

    if(!strcmp(argv[argi], "-us")) {
      if((++argi) < argc) {
        unscuscribe_counter = atol(argv[argi]);
      } else {
        usage(argv[0],sip_local_ip);
        exit(1);
      }
    }

    if(!strcmp(argv[argi], "-d")) {
      if((++argi) < argc) {
        uas_invite_delay = atol(argv[argi]);
      } else {
        usage(argv[0],sip_local_ip);
        exit(1);
      }
    }

  }
  
  strcat(hostname,"_sipua_");
  sprintf(sip_pid,"%d",getpid());
  strcat(hostname,sip_pid);

  sip_status = sip_init_lib(hostname,
                            0,
                            NULL,
                            SIP_API_VERSION);

  printf("SIP User-Agent (%s) IP:%s started using UDP port %d\n",
          hostname,
          sip_local_ip,
          sip_port);

  /* Fill the SIP Call-Handling callback vector */
  memset(&sip_ch_callback, 0, sizeof(sip_call_callback_vector_t));


  sip_ch_callback.sip_call_on_initiate        = sip_call_on_initiate;
  sip_ch_callback.sip_call_on_connect         = sip_call_on_connect;
  sip_ch_callback.sip_call_on_release         = sip_call_on_release;
  sip_ch_callback.sip_call_on_cancel          = sip_call_on_cancel;
  sip_ch_callback.sip_call_on_progress        = sip_call_on_progress;
  sip_ch_callback.sip_call_on_accept          = sip_call_on_accept;
  sip_ch_callback.sip_call_on_get_media       = sip_call_on_get_media;
  sip_ch_callback.sip_call_on_request         = sip_call_on_request;
  sip_ch_callback.sip_call_on_reply           = sip_call_on_reply;
  sip_ch_callback.sip_call_on_event           = sip_call_on_event;
  sip_ch_callback.sip_call_on_evt_subscribe   = sip_call_on_evt_subscribe;
  sip_ch_callback.sip_call_on_evt_notify      = sip_call_on_evt_notify;

  /* Fill the transport info array */
  sip_trp_info[0].trp_name = strdup("my_address");
  sip_trp_info[0].dns_name = NULL;
  sip_trp_info[0].address  = sip_local_ip;
  sip_trp_info[0].port     = sip_port;
  sip_trp_info[0].trp_type = SIP_TRP_UDP;

 
  /* Create the SIP transaction instance */
  sip_status = sip_call_create_instance(&sip_ch_inst,
                                        hostname,
                                        SIP_CALL_ENTITY_UA,
                                        &sip_ch_callback,
                                        sip_trp_info,
                                        sip_nb_trp,
                                        NULL,
                                        NULL);
  if (sip_status != SIP_NORMAL)
  {
    printf("Error in sip_call_create_instance function: %d\n", sip_status);
    exit(1);
  }


  /* Enable the SIP transaction instance */
  sip_status = sip_call_enable_instance(sip_ch_inst);
  if (sip_status != SIP_NORMAL)
  {
    printf("Error in sip_call_enable_instance function: %d\n", sip_status);
    exit(1);
  }

  if ((sip_called_uri)
   && (call_uri(sip_called_uri,
                sip_ch_inst, 
                sip_port,
	        do_body)))
  {
    sip_call_delete_instance(sip_ch_inst);
    exit(1);  
  }


  /* Waiting for incoming messages */
  while (1)
  {
    sip_status = sip_call_deliver_indic(sip_ch_inst,
                                        SIP_FALSE, /* non blocking */
                                        SIP_DELIVER_ALL_MSG,
                                        &sip_remaining_indic);
    if (sip_status != SIP_NORMAL)
    {
      sip_call_delete_instance(sip_ch_inst);
      printf("Error %d in delivering indication\n", sip_status);
      exit(1);
    }
    
    if (sip_exit && auto_exit)
    {
      sleep(1);
      
      if(interactive) {
        printf("Press enter to exit...\n");
        getchar();
      }
      
      sip_call_delete_instance(sip_ch_inst);
      // printf("Exiting\n");
      exit(0);
    }
  }
}

⌨️ 快捷键说明

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