/* * Create new socket/endpoint for communication and returns a descriptor. */ PJ_DEF(pj_status_t) pj_sock_socket(int af, int type, int proto, pj_sock_t *sock) { PJ_CHECK_STACK(); /* Sanity checks. */ PJ_ASSERT_RETURN(sock!=NULL, PJ_EINVAL); PJ_ASSERT_RETURN((unsigned)PJ_INVALID_SOCKET==INVALID_SOCKET, (*sock=PJ_INVALID_SOCKET, PJ_EINVAL)); *sock = WSASocket(af, type, proto, NULL, 0, WSA_FLAG_OVERLAPPED); if (*sock == PJ_INVALID_SOCKET) return PJ_RETURN_OS_ERROR(pj_get_native_netos_error()); #if PJ_SOCK_DISABLE_WSAECONNRESET && \ (!defined(PJ_WIN32_WINCE) || PJ_WIN32_WINCE==0) #ifndef SIO_UDP_CONNRESET #define SIO_UDP_CONNRESET _WSAIOW(IOC_VENDOR,12) #endif /* Disable WSAECONNRESET for UDP. * See https://trac.pjsip.org/repos/ticket/1197 */ if (type==PJ_SOCK_DGRAM) { DWORD dwBytesReturned = 0; BOOL bNewBehavior = FALSE; DWORD rc; rc = WSAIoctl(*sock, SIO_UDP_CONNRESET, &bNewBehavior, sizeof(bNewBehavior), NULL, 0, &dwBytesReturned, NULL, NULL); if (rc==SOCKET_ERROR) { // Ignored.. } } #endif return PJ_SUCCESS; }
/* * Instruct the I/O Queue to write to the handle. */ PJ_DEF(pj_status_t) pj_ioqueue_sendto( pj_ioqueue_key_t *key, pj_ioqueue_op_key_t *op_key, const void *data, pj_ssize_t *length, pj_uint32_t flags, const pj_sockaddr_t *addr, int addrlen) { TRequestStatus reqStatus; TPtrC8 aBuffer; TInetAddr inetAddr; TSockXfrLength aLen; pj_status_t status; PJ_UNUSED_ARG(op_key); // Forcing pending operation is not supported. PJ_ASSERT_RETURN((flags & PJ_IOQUEUE_ALWAYS_ASYNC)==0, PJ_EINVAL); // Return failure if access point is marked as down by app. PJ_SYMBIAN_CHECK_CONNECTION(); // Convert address status = PjSymbianOS::pj2Addr(*(const pj_sockaddr*)addr, addrlen, inetAddr); if (status != PJ_SUCCESS) return status; // Clear flag flags &= ~PJ_IOQUEUE_ALWAYS_ASYNC; aBuffer.Set((const TUint8*)data, (TInt)*length); CPjSocket *pjSock = key->cbObj->get_pj_socket(); pjSock->Socket().SendTo(aBuffer, inetAddr, flags, reqStatus, aLen); User::WaitForRequest(reqStatus); if (reqStatus.Int() != KErrNone) return PJ_RETURN_OS_ERROR(reqStatus.Int()); //At least in UIQ Emulator, aLen.Length() reports incorrect length //for UDP (some newlc.com users seem to have reported this too). //*length = aLen.Length(); return PJ_SUCCESS; }
PJ_DEF(pj_status_t) pj_rwmutex_create(pj_pool_t *pool, const char *name, pj_rwmutex_t **p_mutex) { pj_rwmutex_t *rwm; pj_status_t status; PJ_UNUSED_ARG(name); rwm = PJ_POOL_ALLOC_T(pool, pj_rwmutex_t); PJ_ASSERT_RETURN(rwm, PJ_ENOMEM); status = pthread_rwlock_init(&rwm->rwlock, NULL); if (status != 0) return PJ_RETURN_OS_ERROR(status); *p_mutex = rwm; return PJ_SUCCESS; }
/* * Start listening to incoming connections. */ PJ_DEF(pj_status_t) pj_sock_listen( pj_sock_t sock, int backlog) { PJ_CHECK_STACK(); PJ_ASSERT_RETURN(sock && backlog, PJ_EINVAL); CPjSocket *pjSock = (CPjSocket*)sock; RSocket &rSock = pjSock->Socket(); TInt rc = rSock.Listen((TUint)backlog); if (rc == KErrNone) { return PJ_SUCCESS; } else { return PJ_RETURN_OS_ERROR(rc); } }
/* * Close socket. */ PJ_DEF(pj_status_t) pj_sock_close(pj_sock_t sock) { int rc; PJ_CHECK_STACK(); #if defined(PJ_WIN32) && PJ_WIN32!=0 || \ defined(PJ_WIN64) && PJ_WIN64 != 0 || \ defined(PJ_WIN32_WINCE) && PJ_WIN32_WINCE!=0 rc = closesocket(sock); #else rc = close(sock); #endif if (rc != 0) return PJ_RETURN_OS_ERROR(pj_get_native_netos_error()); else return PJ_SUCCESS; }
int CPjSSLSocket::Connect(CPjSSLSocket_cb cb, void *key, const TInetAddr &local_addr, const TInetAddr &rem_addr, const TDesC8 &servername, const TDesC8 &ciphers) { pj_status_t status; PJ_ASSERT_RETURN(state_ == SSL_STATE_NULL, PJ_EINVALIDOP); status = pj_sock_socket(rem_addr.Family(), pj_SOCK_STREAM(), 0, &sock_); if (status != PJ_SUCCESS) return status; // Apply QoS status = pj_sock_apply_qos2(sock_, qos_type_, &qos_params_, 2, THIS_FILE, NULL); RSocket &rSock = ((CPjSocket*)sock_)->Socket(); local_addr_ = local_addr; if (!local_addr_.IsUnspecified()) { TInt err = rSock.Bind(local_addr_); if (err != KErrNone) return PJ_RETURN_OS_ERROR(err); } cb_ = cb; key_ = key; rem_addr_ = rem_addr; /* Note: the following members only keep the pointer, not the data */ servername_.Set(servername); ciphers_.Set(ciphers); rSock.Connect(rem_addr_, iStatus); SetActive(); state_ = SSL_STATE_CONNECTING; rSock.LocalName(local_addr_); return PJ_EPENDING; }
/* * pj_mutex_trylock() */ PJ_DEF(pj_status_t) pj_mutex_trylock(pj_mutex_t *mutex) { #if PJ_HAS_THREADS int status; PJ_CHECK_STACK(); PJ_ASSERT_RETURN(mutex, PJ_EINVAL); PJ_LOG(6,(mutex->obj_name, "Mutex: thread %s is trying", pj_thread_this()->obj_name)); status = pthread_mutex_trylock( &mutex->mutex ); if (status==0) { #if PJ_DEBUG mutex->owner = pj_thread_this(); pj_ansi_strcpy(mutex->owner_name, mutex->owner->obj_name); ++mutex->nesting_level; PJ_LOG(6,(mutex->obj_name, "Mutex acquired by thread %s (level=%d)", pj_thread_this()->obj_name, mutex->nesting_level)); #else PJ_LOG(6,(mutex->obj_name, "Mutex acquired by thread %s", pj_thread_this()->obj_name)); #endif } else { PJ_LOG(6,(mutex->obj_name, "Mutex: thread %s's trylock() failed", pj_thread_this()->obj_name)); } if (status==0) return PJ_SUCCESS; else return PJ_RETURN_OS_ERROR(status); #else /* PJ_HAS_THREADS */ pj_assert( mutex == (pj_mutex_t*)1); return PJ_SUCCESS; #endif }
/* * Create new socket/endpoint for communication and returns a descriptor. */ PJ_DEF(pj_status_t) pj_sock_socket(int af, int type, int proto, pj_sock_t *sock) { PJ_CHECK_STACK(); /* Sanity checks. */ PJ_ASSERT_RETURN(sock!=NULL, PJ_EINVAL); PJ_ASSERT_RETURN(PJ_INVALID_SOCKET==-1, (*sock=PJ_INVALID_SOCKET, PJ_EINVAL)); *sock = socket(af, type, proto); if (*sock == PJ_INVALID_SOCKET) return PJ_RETURN_OS_ERROR(pj_get_native_netos_error()); else return PJ_SUCCESS; }
PJ_DEF(pj_status_t) pj_file_open( pj_pool_t *pool, const char *pathname, unsigned flags, pj_oshandle_t *fd) { char mode[8]; char *p = mode; PJ_ASSERT_RETURN(pathname && fd, PJ_EINVAL); PJ_UNUSED_ARG(pool); if ((flags & PJ_O_APPEND) == PJ_O_APPEND) { if ((flags & PJ_O_WRONLY) == PJ_O_WRONLY) { *p++ = 'a'; if ((flags & PJ_O_RDONLY) == PJ_O_RDONLY) *p++ = '+'; } else { /* This is invalid. * Can not specify PJ_O_RDONLY with PJ_O_APPEND! */ } } else { if ((flags & PJ_O_RDONLY) == PJ_O_RDONLY) { *p++ = 'r'; if ((flags & PJ_O_WRONLY) == PJ_O_WRONLY) *p++ = '+'; } else { *p++ = 'w'; } } if (p==mode) return PJ_EINVAL; *p++ = 'b'; *p++ = '\0'; *fd = fopen(pathname, mode); if (*fd == NULL) return PJ_RETURN_OS_ERROR(errno); return PJ_SUCCESS; }
/* * Create new socket/endpoint for communication and returns a descriptor. */ PJ_DEF(pj_status_t) pj_sock_socket(int af, int type, int proto, pj_sock_t *p_sock) { TInt rc; PJ_CHECK_STACK(); /* Sanity checks. */ PJ_ASSERT_RETURN(p_sock!=NULL, PJ_EINVAL); // Return failure if access point is marked as down by app. PJ_SYMBIAN_CHECK_CONNECTION(); /* Set proto if none is specified. */ if (proto == 0) { if (type == pj_SOCK_STREAM()) proto = KProtocolInetTcp; else if (type == pj_SOCK_DGRAM()) proto = KProtocolInetUdp; } /* Create Symbian RSocket */ RSocket rSock; if (PjSymbianOS::Instance()->Connection()) rc = rSock.Open(PjSymbianOS::Instance()->SocketServ(), af, type, proto, *PjSymbianOS::Instance()->Connection()); else rc = rSock.Open(PjSymbianOS::Instance()->SocketServ(), af, type, proto); if (rc != KErrNone) return PJ_RETURN_OS_ERROR(rc); /* Wrap Symbian RSocket into PJLIB's CPjSocket, and return to caller */ CPjSocket *pjSock = new CPjSocket(af, type, rSock); *p_sock = (pj_sock_t)pjSock; return PJ_SUCCESS; }
/* * Send data */ PJ_DEF(pj_status_t) pj_sock_send(pj_sock_t sock, const void *buf, pj_ssize_t *len, unsigned flags) { PJ_CHECK_STACK(); PJ_ASSERT_RETURN(len, PJ_EINVAL); #ifdef MSG_NOSIGNAL /* Suppress SIGPIPE. See https://trac.pjsip.org/repos/ticket/1538 */ flags |= MSG_NOSIGNAL; #endif *len = send(sock, (const char*)buf, *len, flags); if (*len < 0) return PJ_RETURN_OS_ERROR(pj_get_native_netos_error()); else return PJ_SUCCESS; }
/* * Set the thread priority. */ PJ_DEF(pj_status_t) pj_thread_set_prio(pj_thread_t *thread, int prio) { #if PJ_HAS_THREADS PJ_ASSERT_RETURN(thread, PJ_EINVAL); PJ_ASSERT_RETURN(prio>=THREAD_PRIORITY_IDLE && prio<=THREAD_PRIORITY_TIME_CRITICAL, PJ_EINVAL); if (SetThreadPriority(thread->hthread, prio) == FALSE) return PJ_RETURN_OS_ERROR(GetLastError()); return PJ_SUCCESS; #else PJ_UNUSED_ARG(thread); PJ_UNUSED_ARG(prio); pj_assert("pj_thread_set_prio() called in non-threading mode!"); return PJ_EINVALIDOP; #endif }
/* * Bind socket. */ PJ_DEF(pj_status_t) pj_sock_bind( pj_sock_t sock, const pj_sockaddr_t *addr, int len) { PJ_CHECK_STACK(); PJ_ASSERT_RETURN(addr && len >= (int)sizeof(struct sockaddr_in), PJ_EINVAL); CHECK_ADDR_LEN(addr, len); pj_int32_t val = 1; int rc = pj_sock_setsockopt(sock, pj_SOL_SOCKET(), pj_SO_REUSEADDR(), &val, sizeof(val)); if (rc != 0) return rc; if (bind(sock, (struct sockaddr*)addr, len) != 0) return PJ_RETURN_OS_ERROR(pj_get_native_netos_error()); else return PJ_SUCCESS; }
/* * Send data. */ PJ_DEF(pj_status_t) pj_sock_sendto(pj_sock_t sock, const void *buf, pj_ssize_t *len, unsigned flags, const pj_sockaddr_t *to, int tolen) { PJ_CHECK_STACK(); PJ_ASSERT_RETURN(len, PJ_EINVAL); CHECK_ADDR_LEN(to, tolen); *len = sendto(sock, (const char*)buf, *len, flags, (const struct sockaddr*)to, tolen); if (*len < 0) return PJ_RETURN_OS_ERROR(pj_get_native_netos_error()); else return PJ_SUCCESS; }
/* * pj_sem_post() */ PJ_DEF(pj_status_t) pj_sem_post(pj_sem_t *sem) { #if PJ_HAS_THREADS int result; PJ_LOG(6, (sem->obj_name, "Semaphore released by thread %s", pj_thread_this(sem->inst_id)->obj_name)); #if defined(PJ_DARWINOS) && PJ_DARWINOS!=0 result = dispatch_semaphore_signal(sem->sem); #else result = sem_post( sem->sem ); #endif if (result == 0) return PJ_SUCCESS; else return PJ_RETURN_OS_ERROR(pj_get_native_os_error()); #else pj_assert( sem == (pj_sem_t*) 1); return PJ_SUCCESS; #endif }
/* * Receive data. */ PJ_DEF(pj_status_t) pj_sock_recvfrom(pj_sock_t sock, void *buf, pj_ssize_t *len, unsigned flags, pj_sockaddr_t *from, int *fromlen) { PJ_CHECK_STACK(); PJ_ASSERT_RETURN(buf && len, PJ_EINVAL); PJ_ASSERT_RETURN(from && fromlen, (*len=-1, PJ_EINVAL)); *len = recvfrom(sock, (char*)buf, *len, flags, (struct sockaddr*)from, (socklen_t*)fromlen); if (*len < 0) return PJ_RETURN_OS_ERROR(pj_get_native_netos_error()); else { PJ_SOCKADDR_RESET_LEN(from); return PJ_SUCCESS; } }
/* * pj_file_getstat() */ PJ_DEF(pj_status_t) pj_file_getstat(const char *filename, pj_file_stat *statbuf) { struct stat buf; PJ_ASSERT_RETURN(filename && statbuf, PJ_EINVAL); if (stat(filename, &buf) != 0) { return PJ_RETURN_OS_ERROR(errno); } statbuf->size = buf.st_size; statbuf->ctime.sec = buf.st_ctime; statbuf->ctime.msec = 0; statbuf->mtime.sec = buf.st_mtime; statbuf->mtime.msec = 0; statbuf->atime.sec = buf.st_atime; statbuf->atime.msec = 0; return PJ_SUCCESS; }
/* * Connect socket. */ PJ_DEF(pj_status_t) pj_sock_connect( pj_sock_t sockfd, const pj_sockaddr_t *addr, int namelen) { long err; mm_segment_t oldfs; PJ_CHECK_STACK(); oldfs = get_fs(); set_fs(KERNEL_DS); err = sys_connect( sockfd, (void*)addr, namelen ); set_fs(oldfs); if (err) return PJ_RETURN_OS_ERROR(-err); else return PJ_SUCCESS; }
/* * Get socket name. */ PJ_DEF(pj_status_t) pj_sock_getsockname( pj_sock_t sockfd, pj_sockaddr_t *addr, int *namelen) { mm_segment_t oldfs; int err; PJ_CHECK_STACK(); oldfs = get_fs(); set_fs(KERNEL_DS); err = sys_getsockname( sockfd, addr, namelen ); set_fs(oldfs); if (err) return PJ_RETURN_OS_ERROR(-err); else return PJ_SUCCESS; }
/* * Send data. */ PJ_DEF(pj_status_t) pj_sock_sendto(pj_sock_t sock, const void *buf, pj_ssize_t *len, unsigned flags, const pj_sockaddr_t *to, int tolen) { pj_status_t status; PJ_CHECK_STACK(); PJ_ASSERT_RETURN(sock && buf && len, PJ_EINVAL); // Return failure if access point is marked as down by app. PJ_SYMBIAN_CHECK_CONNECTION(); CPjSocket *pjSock = (CPjSocket*)sock; RSocket &rSock = pjSock->Socket(); // Only supports AF_INET for now PJ_ASSERT_RETURN(tolen>=(int)sizeof(pj_sockaddr_in), PJ_EINVAL); TInetAddr inetAddr; status = PjSymbianOS::pj2Addr(*(pj_sockaddr*)to, tolen, inetAddr); if (status != PJ_SUCCESS) return status; TPtrC8 data((const TUint8*)buf, (TInt)*len); TRequestStatus reqStatus; TSockXfrLength sentLen; rSock.SendTo(data, inetAddr, flags, reqStatus, sentLen); User::WaitForRequest(reqStatus); if (reqStatus.Int()==KErrNone) { //For some reason TSockXfrLength is not returning correctly! //*len = (TInt) sentLen.Length(); return PJ_SUCCESS; } else return PJ_RETURN_OS_ERROR(reqStatus.Int()); }
/* * Load BladeEncoder DLL. */ static pj_status_t init_blade_dll(void) { if (BladeDLL.refCount == 0) { #define GET_PROC(type, name) \ BladeDLL.name = (type)GetProcAddress(BladeDLL.hModule, PJ_T(#name)); \ if (BladeDLL.name == NULL) { \ PJ_LOG(1,(THIS_FILE, "Unable to find %s in %s", #name, DLL_NAME)); \ return PJ_RETURN_OS_ERROR(GetLastError()); \ } BE_VERSION beVersion; BladeDLL.hModule = (void*)LoadLibrary(DLL_NAME); if (BladeDLL.hModule == NULL) { pj_status_t status = PJ_RETURN_OS_ERROR(GetLastError()); char errmsg[PJ_ERR_MSG_SIZE]; pj_strerror(status, errmsg, sizeof(errmsg)); PJ_LOG(1,(THIS_FILE, "Unable to load %s: %s", DLL_NAME, errmsg)); return status; } GET_PROC(BEINITSTREAM, beInitStream); GET_PROC(BEENCODECHUNK, beEncodeChunk); GET_PROC(BEDEINITSTREAM, beDeinitStream); GET_PROC(BECLOSESTREAM, beCloseStream); GET_PROC(BEVERSION, beVersion); GET_PROC(BEWRITEVBRHEADER, beWriteVBRHeader); GET_PROC(BEWRITEINFOTAG, beWriteInfoTag); #undef GET_PROC BladeDLL.beVersion(&beVersion); PJ_LOG(4,(THIS_FILE, "%s encoder v%d.%d loaded (%s)", DLL_NAME, beVersion.byMajorVersion, beVersion.byMinorVersion, beVersion.zHomepage)); } ++BladeDLL.refCount; return PJ_SUCCESS; }
/* * Accept incoming connections */ PJ_DEF(pj_status_t) pj_sock_accept( pj_sock_t sockfd, pj_sock_t *newsockfd, pj_sockaddr_t *addr, int *addrlen) { long err; PJ_CHECK_STACK(); PJ_ASSERT_RETURN(newsockfd != NULL, PJ_EINVAL); err = sys_accept( sockfd, addr, addrlen); if (err < 0) { *newsockfd = PJ_INVALID_SOCKET; return PJ_RETURN_OS_ERROR(-err); } else { *newsockfd = err; return PJ_SUCCESS; } }
/* * Accept incoming connections */ PJ_DEF(pj_status_t) pj_sock_accept( pj_sock_t serverfd, pj_sock_t *newsock, pj_sockaddr_t *addr, int *addrlen) { PJ_CHECK_STACK(); PJ_ASSERT_RETURN(serverfd && newsock, PJ_EINVAL); CPjSocket *pjSock = (CPjSocket*)serverfd; RSocket &rSock = pjSock->Socket(); // Create a 'blank' socket RSocket newSock; newSock.Open(PjSymbianOS::Instance()->SocketServ()); // Call Accept() TRequestStatus reqStatus; rSock.Accept(newSock, reqStatus); User::WaitForRequest(reqStatus); if (reqStatus != KErrNone) { return PJ_RETURN_OS_ERROR(reqStatus.Int()); } // Create PJ socket CPjSocket *newPjSock = new CPjSocket(pjSock->GetAf(), pjSock->GetSockType(), newSock); newPjSock->SetConnected(true); *newsock = (pj_sock_t) newPjSock; if (addr && addrlen) { return pj_sock_getpeername(*newsock, addr, addrlen); } return PJ_SUCCESS; }
/* * pj_file_move() */ PJ_DEF(pj_status_t) pj_file_move( const char *oldname, const char *newname) { PJ_DECL_UNICODE_TEMP_BUF(woldname,256) PJ_DECL_UNICODE_TEMP_BUF(wnewname,256) BOOL rc; PJ_ASSERT_RETURN(oldname!=NULL && newname!=NULL, PJ_EINVAL); #if PJ_WIN32_WINNT >= 0x0400 rc = MoveFileEx(PJ_STRING_TO_NATIVE(oldname,woldname,sizeof(woldname)), PJ_STRING_TO_NATIVE(newname,wnewname,sizeof(wnewname)), MOVEFILE_COPY_ALLOWED|MOVEFILE_REPLACE_EXISTING); #else rc = MoveFile(PJ_STRING_TO_NATIVE(oldname,woldname,sizeof(woldname)), PJ_STRING_TO_NATIVE(newname,wnewname,sizeof(wnewname))); #endif if (!rc) return PJ_RETURN_OS_ERROR(GetLastError()); return PJ_SUCCESS; }
/* * pj_thread_join() */ PJ_DEF(pj_status_t) pj_thread_join(pj_thread_t *p) { pj_thread_t *rec = (pj_thread_t *)p; DWORD rc; PJ_CHECK_STACK(); PJ_ASSERT_RETURN(p, PJ_EINVAL); if (p == pj_thread_this()) return PJ_ECANCELLED; PJ_LOG(6, (pj_thread_this()->obj_name, "Joining thread %s", p->obj_name)); rc = WaitForSingleObject(rec->hthread, INFINITE); if (rc==WAIT_OBJECT_0) return PJ_SUCCESS; else if (rc==WAIT_TIMEOUT) return PJ_ETIMEDOUT; else return PJ_RETURN_OS_ERROR(GetLastError()); }
/* * pj_thread_sleep() */ PJ_DEF(pj_status_t) pj_thread_sleep(unsigned msec) { /* TODO: should change this to something like PJ_OS_HAS_NANOSLEEP */ #if defined(PJ_RTEMS) && PJ_RTEMS!=0 enum { NANOSEC_PER_MSEC = 1000000 }; struct timespec req; PJ_CHECK_STACK(); req.tv_sec = msec / 1000; req.tv_nsec = (msec % 1000) * NANOSEC_PER_MSEC; if (nanosleep(&req, NULL) == 0) return PJ_SUCCESS; return PJ_RETURN_OS_ERROR(pj_get_native_os_error()); #else PJ_CHECK_STACK(); pj_set_os_error(0); usleep(msec * 1000); /* MacOS X (reported on 10.5) seems to always set errno to ETIMEDOUT. * It does so because usleep() is declared to return int, and we're * supposed to check for errno only when usleep() returns non-zero. * Unfortunately, usleep() is declared to return void in other platforms * so it's not possible to always check for the return value (unless * we add a detection routine in autoconf). * * As a workaround, here we check if ETIMEDOUT is returned and * return successfully if it is. */ if (pj_get_native_os_error() == ETIMEDOUT) return PJ_SUCCESS; return pj_get_os_error(); #endif /* PJ_RTEMS */ }
/* * Create new socket/endpoint for communication and returns a descriptor. */ PJ_DEF(pj_status_t) pj_sock_socket(int af, int type, int proto, pj_sock_t *sock) { PJ_CHECK_STACK(); /* Sanity checks. */ PJ_ASSERT_RETURN(sock!=NULL, PJ_EINVAL); PJ_ASSERT_RETURN(PJ_INVALID_SOCKET==-1, (*sock=PJ_INVALID_SOCKET, PJ_EINVAL)); *sock = socket(af, type, proto); if (*sock == PJ_INVALID_SOCKET) return PJ_RETURN_OS_ERROR(pj_get_native_netos_error()); else { pj_int32_t val = 1; if (type == pj_SOCK_STREAM()) { pj_sock_setsockopt(*sock, pj_SOL_SOCKET(), pj_SO_NOSIGPIPE(), &val, sizeof(val)); } #if defined(PJ_SOCK_HAS_IPV6_V6ONLY) && PJ_SOCK_HAS_IPV6_V6ONLY != 0 if (af == PJ_AF_INET6) { pj_sock_setsockopt(*sock, PJ_SOL_IPV6, IPV6_V6ONLY, &val, sizeof(val)); } #endif #if defined(PJ_IPHONE_OS_HAS_MULTITASKING_SUPPORT) && \ PJ_IPHONE_OS_HAS_MULTITASKING_SUPPORT!=0 if (type == pj_SOCK_DGRAM()) { pj_sock_setsockopt(*sock, pj_SOL_SOCKET(), SO_NOSIGPIPE, &val, sizeof(val)); } #endif return PJ_SUCCESS; } }
PJ_DEF(pj_status_t) pj_sem_trywait2(pj_sem_t *sem) { #if 1 pj_status_t result; uint64_t delay_ms = 1000000; dispatch_time_t delay_t = dispatch_time(DISPATCH_TIME_NOW, delay_ms); if(dispatch_semaphore_wait(sem->sem, delay_t)){ usleep(1000); return PJ_RETURN_OS_ERROR(pj_get_native_os_error()); }else return PJ_SUCCESS; #else pj_status_t st = -1; unsigned long start_t, curr_t; //uint64_t tstart; //struct timespec tstart={0,0}, tend={0,0}; //clock_serv_t cclock; //clock_gettime(cclock , &tstart); struct timeval tstart,tcurr; gettimeofday(&tstart, NULL); start_t = 1000000*tstart.tv_sec+ tstart.tv_usec; while(st = pj_sem_trywait(sem) == -1 ){ if(errno == EAGAIN){ //clock_gettime(cclock, &tend); gettimeofday(&tcurr, NULL); curr_t = 1000000*tcurr.tv_sec + tcurr.tv_usec; if(curr_t-start_t > 1000) { st = -1; break; } else usleep(10); }else{ st = -1; break; } } return st; #endif }
/* * Get socket option. */ PJ_DEF(pj_status_t) pj_sock_getsockopt( pj_sock_t sockfd, pj_uint16_t level, pj_uint16_t optname, void *optval, int *optlen) { mm_segment_t oldfs; long err; PJ_CHECK_STACK(); oldfs = get_fs(); set_fs(KERNEL_DS); err = sys_getsockopt( sockfd, level, optname, optval, optlen); set_fs(oldfs); if (err) return PJ_RETURN_OS_ERROR(-err); else return PJ_SUCCESS; }
/* * Create new socket/endpoint for communication and returns a descriptor. */ PJ_DEF(pj_status_t) pj_sock_socket(int af, int type, int proto, pj_sock_t *sock_fd) { long result; PJ_CHECK_STACK(); /* Sanity checks. */ PJ_ASSERT_RETURN(PJ_INVALID_SOCKET == -1 && sock_fd != NULL, PJ_EINVAL); /* Initialize returned socket */ *sock_fd = PJ_INVALID_SOCKET; /* Create socket. */ result = sys_socket(af, type, proto); if (result < 0) { return PJ_RETURN_OS_ERROR((-result)); } *sock_fd = result; return PJ_SUCCESS; }