EXPORT int iaxc_initialize(int num_calls) { int i; int port; os_init(); setup_jb_output(); MUTEXINIT(&iaxc_lock); MUTEXINIT(&event_queue_lock); iaxc_set_audio_prefs(0); if ( iaxc_recvfrom != (iaxc_recvfrom_t)recvfrom ) iax_set_networking(iaxc_sendto, iaxc_recvfrom); /* Note that iax_init() only sets up the receive port when the * sendto/recvfrom functions have not been replaced. We need * to call iaxc_init in either case because there is other * initialization beyond the socket setup that needs to be done. */ if ( (port = iax_init(source_udp_port)) < 0 ) { iaxci_usermsg(IAXC_ERROR, "Fatal error: failed to initialize iax with port %d", port); return -1; } if ( iaxc_recvfrom == (iaxc_recvfrom_t)recvfrom ) iaxci_bound_port = port; else iaxci_bound_port = -1; /* tweak the jitterbuffer settings */ iax_set_jb_target_extra( jb_target_extra ); max_calls = num_calls; /* initialize calls */ if ( max_calls <= 0 ) max_calls = 1; /* 0 == Default? */ /* calloc zeroes for us */ calls = (struct iaxc_call *)calloc(sizeof(struct iaxc_call), max_calls); if ( !calls ) { iaxci_usermsg(IAXC_ERROR, "Fatal error: can't allocate memory"); return -1; } selected_call = -1; for ( i = 0; i < max_calls; i++ ) { strncpy(calls[i].callerid_name, DEFAULT_CALLERID_NAME, IAXC_EVENT_BUFSIZ); strncpy(calls[i].callerid_number, DEFAULT_CALLERID_NUMBER, IAXC_EVENT_BUFSIZ); } if ( !test_mode ) { #ifndef AUDIO_ALSA if ( pa_initialize(&audio_driver, 8000) ) { iaxci_usermsg(IAXC_ERROR, "failed pa_initialize"); return -1; } #else /* TODO: It is unknown whether this stuff for direct access to * alsa should be left in iaxclient. We're leaving it in here for * the time being, but unless it becomes clear that someone cares * about having it, it will be removed. Also note that portaudio * is capable of using alsa. This is another reason why this * direct alsa access may be unneeded. */ if ( alsa_initialize(&audio_driver, 8000) ) return -1; #endif } #ifdef USE_VIDEO if ( video_initialize() ) iaxci_usermsg(IAXC_ERROR, "iaxc_initialize: cannot initialize video!\n"); #endif /* Default audio format capabilities */ audio_format_capability = IAXC_FORMAT_ULAW | IAXC_FORMAT_ALAW | #ifdef CODEC_GSM IAXC_FORMAT_GSM | #endif IAXC_FORMAT_SPEEX; audio_format_preferred = IAXC_FORMAT_SPEEX; return 0; }
EXPORT int iaxc_initialize(int num_calls) { printf("ESTOY IAXC 0\n"); int i; int port; os_init(); setup_jb_output(); MUTEXINIT(&iaxc_lock); MUTEXINIT(&event_queue_lock); iaxc_set_audio_prefs(0); if ( iaxc_recvfrom != (iaxc_recvfrom_t)recvfrom ) iax_set_networking(iaxc_sendto, iaxc_recvfrom); /* Note that iax_init() only sets up the receive port when the * sendto/recvfrom functions have not been replaced. We need * to call iaxc_init in either case because there is other * initialization beyond the socket setup that needs to be done. */ if ( (port = iax_init(source_udp_port)) < 0 ) { iaxci_usermsg(IAXC_ERROR, "Fatal error: failed to initialize iax with port %d", port); return -1; } if ( iaxc_recvfrom == (iaxc_recvfrom_t)recvfrom ) iaxci_bound_port = port; else iaxci_bound_port = -1; /* tweak the jitterbuffer settings */ iax_set_jb_target_extra( jb_target_extra ); max_calls = num_calls; /* initialize calls */ if ( max_calls <= 0 ) max_calls = 1; /* 0 == Default? */ /* calloc zeroes for us */ calls = (struct iaxc_call *)calloc(sizeof(struct iaxc_call), max_calls); if ( !calls ) { iaxci_usermsg(IAXC_ERROR, "Fatal error: can't allocate memory"); return -1; } selected_call = -1; for ( i = 0; i < max_calls; i++ ) { strncpy(calls[i].callerid_name, DEFAULT_CALLERID_NAME, IAXC_EVENT_BUFSIZ); strncpy(calls[i].callerid_number, DEFAULT_CALLERID_NUMBER, IAXC_EVENT_BUFSIZ); } printf("ESTOY IAXC\n"); if ( alsa_initialize(&audio_driver, 8000) ) { iaxci_usermsg(IAXC_ERROR, "failed alsa_initialize"); return -1; } #ifdef USE_VIDEO if ( video_initialize() ) iaxci_usermsg(IAXC_ERROR, "iaxc_initialize: cannot initialize video!\n"); #endif /* Default audio format capabilities */ audio_format_capability = IAXC_FORMAT_ULAW | IAXC_FORMAT_ALAW | #ifdef CODEC_GSM IAXC_FORMAT_GSM | #endif IAXC_FORMAT_SPEEX; audio_format_preferred = IAXC_FORMAT_SPEEX; return 0; }
int Iaxc_Init (Tcl_Interp *interp) { iaxcCmd *cmdPtr; Tcl_Obj *codec_val, *codec_name, *evt_val, *evt_name; if (Tcl_InitStubs(interp, "8.3", 0) == NULL) return TCL_ERROR; MUTEXINIT(&head_mutex); evt_list = Tcl_NewListObj(0, NULL); /* iaxc package commands */ for (cmdPtr = commands; cmdPtr->name != NULL; cmdPtr++) { Tcl_CreateObjCommand(interp, cmdPtr->name, cmdPtr->objProc, (ClientData) "::",(Tcl_CmdDeleteProc *)NULL); Tcl_CreateObjCommand(interp, cmdPtr->name2, cmdPtr->objProc, (ClientData) "::iaxc::",(Tcl_CmdDeleteProc *)NULL); } if (Tcl_Eval(interp, "namespace eval ::iaxc namespace export *") == TCL_ERROR) return TCL_ERROR; /* * set available codecs on ::iaxc namespace */ codec_val = Tcl_NewIntObj(1 << 1); codec_name = Tcl_NewStringObj("::iaxc::IAXC_FORMAT_GSM", -1); Tcl_ObjSetVar2(interp, codec_name, NULL, codec_val, 0); codec_val = Tcl_NewIntObj(1 << 2); codec_name = Tcl_NewStringObj("::iaxc::IAXC_FORMAT_ULAW", -1); Tcl_ObjSetVar2(interp, codec_name, NULL, codec_val, 0); codec_val = Tcl_NewIntObj(1 << 3); codec_name = Tcl_NewStringObj("::iaxc::IAXC_FORMAT_ALAW", -1); Tcl_ObjSetVar2(interp, codec_name, NULL, codec_val, 0); codec_val = Tcl_NewIntObj(1 << 9); codec_name = Tcl_NewStringObj("::iaxc::IAXC_FORMAT_SPEEX", -1); Tcl_ObjSetVar2(interp, codec_name, NULL, codec_val, 0); codec_val = Tcl_NewIntObj(1 << 10); codec_name = Tcl_NewStringObj("::iaxc::IAXC_FORMAT_ILBC", -1); Tcl_ObjSetVar2(interp, codec_name, NULL, codec_val, 0); /* * set available event types */ evt_val = Tcl_NewStringObj("text", -1); evt_name = Tcl_NewStringObj("::iaxc::IAXC_EVENT_TEXT", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); evt_val = Tcl_NewStringObj("levels", -1); evt_name = Tcl_NewStringObj("::iaxc::IAXC_EVENT_LEVELS", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); evt_val = Tcl_NewStringObj("state", -1); evt_name = Tcl_NewStringObj("::iaxc::IAXC_EVENT_STATE", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); evt_val = Tcl_NewStringObj("netstat", -1); evt_name = Tcl_NewStringObj("::iaxc::IAXC_EVENT_NETSTAT", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); evt_val = Tcl_NewStringObj("url", -1); evt_name = Tcl_NewStringObj("::iaxc::IAXC_EVENT_URL", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); evt_val = Tcl_NewStringObj("video", -1); evt_name = Tcl_NewStringObj("::iaxc::IAXC_EVENT_VIDEO", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); evt_val = Tcl_NewStringObj("registration", -1); evt_name = Tcl_NewStringObj("::iaxc::IAXC_EVENT_REGISTRATION", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); /* * available states for a call (contained in an state event) */ evt_val = Tcl_NewIntObj(IAXC_CALL_STATE_FREE); evt_name = Tcl_NewStringObj("::iaxc::IAXC_CALL_STATE_FREE", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); evt_val = Tcl_NewIntObj(IAXC_CALL_STATE_ACTIVE); evt_name = Tcl_NewStringObj("::iaxc::IAXC_CALL_STATE_ACTIVE", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); evt_val = Tcl_NewIntObj(IAXC_CALL_STATE_OUTGOING); evt_name = Tcl_NewStringObj("::iaxc::IAXC_CALL_STATE_OUTGOING", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); evt_val = Tcl_NewIntObj(IAXC_CALL_STATE_RINGING); evt_name = Tcl_NewStringObj("::iaxc::IAXC_CALL_STATE_RINGING", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); evt_val = Tcl_NewIntObj(IAXC_CALL_STATE_COMPLETE); evt_name = Tcl_NewStringObj("::iaxc::IAXC_CALL_STATE_COMPLETE", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); evt_val = Tcl_NewIntObj(IAXC_CALL_STATE_SELECTED); evt_name = Tcl_NewStringObj("::iaxc::IAXC_CALL_STATE_SELECTED", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); evt_val = Tcl_NewIntObj(IAXC_CALL_STATE_BUSY); evt_name = Tcl_NewStringObj("::iaxc::IAXC_CALL_STATE_BUSY", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); evt_val = Tcl_NewIntObj(IAXC_CALL_STATE_TRANSFER); evt_name = Tcl_NewStringObj("::iaxc::IAXC_CALL_STATE_TRANSFER", -1); Tcl_ObjSetVar2(interp, evt_name, NULL, evt_val, 0); Tcl_PkgProvide(interp, "iaxc", "0.1"); return TCL_OK; }
//大家可以看看笔者的函数命名习惯,基本遵循匈牙利命名法,即单词首字母大写 //MRSW 是Multi Read and Signal Write(多读和单写)的缩写 //MRSWLock 前缀表示单写多读锁 //中间一个“_”分割符,后面是函数的功能描述Greate,创建,Destroy,摧毁,等等 void MRSWLock_Create(STonyXiaoMultiReadSingleWriteLock* pLock) { MUTEXINIT(&(pLock->m_Lock)); //初始化内部锁 pLock->m_nReadCount = 0; //初始化读计数器 pLock->m_bWriteFlag = false; //初始化写标志 }