Example #1
0
static void *sillyThreadFn(void *args)
{
	int *sleepTime = (int *)args;
	assert(sleepTime);

	/* we don't want you sleeping forever, so arg > 20 is tossed */
	assert(*sleepTime >= 0 && *sleepTime <= 20);

    	sleep(*sleepTime);

	/* make sure we let the Thread manager know we're gone */
	ThreadExit(ThreadSelf());
}
Example #2
0
File: lock.c Project: blakawk/Aio4c
Lock* _TakeLock(char* file, int line, Lock* lock) {
#ifndef AIO4C_WIN32
    ErrorCode code = AIO4C_ERROR_CODE_INITIALIZER;
#endif /* AIO4C_WIN32 */
    Thread* current = ThreadSelf();

    ProbeTimeStart(AIO4C_TIME_PROBE_BLOCK);

    if (current != NULL) {
        ThreadSetState(current, AIO4C_THREAD_STATE_BLOCKED);
    }

    dthread("%s:%d: %s lock %p\n", file, line, (current!=NULL)?ThreadGetName(current):NULL, (void*)lock);

#ifndef AIO4C_WIN32
    if ((code.error = pthread_mutex_lock(&lock->mutex)) != 0) {
        code.lock = lock;

        if (current != NULL) {
            ThreadSetState(current, AIO4C_THREAD_STATE_RUNNING);
        }

        Raise(AIO4C_LOG_LEVEL_ERROR, AIO4C_THREAD_LOCK_ERROR_TYPE, AIO4C_THREAD_LOCK_TAKE_ERROR, &code);
        return NULL;
    }
#else /* AIO4C_WIN32 */
    EnterCriticalSection(&lock->mutex);
#endif /* AIO4C_WIN32 */

    lock->owner = current;
    lock->state = AIO4C_LOCK_STATE_LOCKED;

    if (current != NULL) {
        ThreadSetState(current, AIO4C_THREAD_STATE_RUNNING);
    }

    ProbeTimeEnd(AIO4C_TIME_PROBE_BLOCK);

    return lock;
}
Example #3
0
File: lock.c Project: blakawk/Aio4c
Lock* _ReleaseLock(char* file, int line, Lock* lock) {
    Thread* current = ThreadSelf();
#ifndef AIO4C_WIN32
    ErrorCode code = AIO4C_ERROR_CODE_INITIALIZER;
#endif /* AIO4C_WIN32 */

    dthread("%s:%d: %s unlock %p\n", file, line, (current!=NULL)?ThreadGetName(current):NULL, (void*)lock);

    lock->state = AIO4C_LOCK_STATE_FREE;
    lock->owner = NULL;

#ifndef AIO4C_WIN32
    if ((code.error = pthread_mutex_unlock(&lock->mutex)) != 0) {
        code.lock = lock;
        Raise(AIO4C_LOG_LEVEL_WARN, AIO4C_THREAD_LOCK_ERROR_TYPE, AIO4C_THREAD_LOCK_RELEASE_ERROR, &code);
        return NULL;
    }
#else /* AIO4C_WIN32 */
    LeaveCriticalSection(&lock->mutex);
#endif /* AIO4C_WIN32 */

    return lock;
}
static void *DcpRecDownloadThread( void *args )
{
	int ret;
	int readLen = MAX_RECORD_DATA_SEND_PACKET_SIZE;
	REC_DOWNLOAD_T *pRecDownload = (REC_DOWNLOAD_T *)args;

	ThreadDetach( ThreadSelf() );
    
	SVPrint( "%s start!\r\n", __FUNCTION__ );
	while( 1 )
    {
    	ret = Read( pRecDownload->fd, pRecDownload->sendPack.dataBuf, readLen );
    	if( ret > 0 )
        {
        	pRecDownload->sendPack.packHead.len = ret;            
        	pRecDownload->len = pRecDownload->sendPack.packHead.len 
                                + sizeof(pRecDownload->sendPack.packHead);
            
        	ret = Sendn( pRecDownload->socket, &pRecDownload->sendPack.packHead, pRecDownload->len );
            
        	if( ret != 0 )
            {
            	break; 
            }
        }
    	else
        {
        	break; 
        }
    }
    
	ReleaseRecDownload( pRecDownload );
    
	SVPrint( "%s stop!\r\n", __FUNCTION__ );
    
	return NULL;
}
Example #5
0
////////////////////////////////////////////////////
// 功能: 
// 输入: 
// 输出:
// 返回: 
// 说明: 
////////////////////////////////////////////////////
static void JzThreadRecordFile(DWORD p)
{
	PAK_OBJECT obj;
	PAK_VFILE vfile;
	PMEDIA_TASK task;
	MESSAGE msg;
	int recsize;
	int samp_size;
	void *buf_in;
	BYTE *fade_buf;
	int msgid;
	int wsize,samp_time;
	int obj_del = 1;
	int fade_len;
	int fade_record = RECORD_FADE;

	// 获取打开信息
	obj = (PAK_OBJECT)p;
	task = &obj->Task;
	vfile = &obj->File;
	if(!task->AChannels)
		task->AChannels = 1;
	if(!task->ASamplerate)
		task->ASamplerate = 8000;
	
	// 写入头信息
	samp_size = 8192 * 2;
	msgid = 0;
	WaveFileHead.bytes_per_samp = task->AChannels * 2;
	WaveFileHead.bytes_per_sec = WaveFileHead.bytes_per_samp * task->ASamplerate;
	WaveFileHead.num_chans = task->AChannels;
	WaveFileHead.sample_rate = task->ASamplerate;
	if( task->MediaType == AK_REC_TYPE_WAVE)
	{
		if(JzCbFileWrite(&WaveFileHead, sizeof(WAVE_HEADER),1,vfile) != sizeof(WAVE_HEADER))
		{
			*obj->bReady = -1;
			goto ThreadEnd;
		}
	}

	// 打开音频编码库
	buf_in = kmalloc(samp_size);
	if(buf_in == NULL)
	{
		*obj->bReady = -1;
		goto ThreadEnd;
	}

	// 打开ADC设备
	obj->hDac = AdcOpen(task->ASamplerate, task->AChannels);
	if(obj->hDac == NULL)
	{
		kdebug(mod_audio, PRINT_ERROR, "ADC device open failed! CH: %d, %dHz\n", task->AChannels, task->ASamplerate);
		kfree(buf_in);
		*obj->bReady = -1;
		goto ThreadEnd;
	}
	AdcSetVolume(obj->hDac, obj->Task.Volume);
	AdcSetEq(obj->hDac, obj->Task.Eq);

	// 发送WM_MEDIA_OPEN消息
	if(task->hWnd)
	{
		msg.hWnd = task->hWnd;
		msg.Data.v = 0;
		msg.hWndSrc = 0;
		msg.MsgId = WM_MEDIA_OPEN;
		msg.Param = 0;
	#if defined(STC_EXP)
		sGuiMsgPutMsg(&msg);
	#else
		GuiMsgPutMsg(&msg);
	#endif
	}
	
	// 等待条件,写入数据
	*obj->bReady = 1;
	recsize = 0;
	fRecodeWav = 1;
	while(!obj->bClose && !obj->bTerminate)
	{
		int i;
		
		// 从DA读取PCM数据
		for(i=0; i<8; i++)
		{
			JzSrvProcMsg(obj);
			wsize = AdcRead(obj->hDac, (short*)((DWORD)buf_in+(i*samp_size)/8), samp_size/8);
			samp_time = (samp_size * 1000 / 8) / (task->ASamplerate * task->AChannels * sizeof(short)) ;

			if( fade_record )
			{	//fade时,不进行时间计算,递减fade时间
				if( fade_record > samp_time )
					fade_record -= samp_time;
				else
					fade_record = 0;
			}
			else	//fade结束,可以进行时间计算
				obj->RecDuration += samp_time;
		}

		if( !fade_record )
			recsize += samp_size;
		
		// 检查录音时间是否结束
		if(obj->Task.Duration && (obj->RecDuration >= obj->Task.Duration))
		{
			recsize -= samp_size;
			obj->bClose = 1;
			break;
		}

		// 直接把PCM数据写入文件
		if( !fade_record )
		{
			wsize = JzCbFileWrite(buf_in, samp_size,1,vfile);
			if(wsize != samp_size)
			{
				if(wsize > 0)
					recsize -= samp_size - wsize;
				else
					recsize -= samp_size;
				obj->bClose = 2;
				break;
			}
		}

		// 处理控制消息
		JzSrvProcMsg(obj);
		while(obj->bRecPause && !obj->bClose && !obj->bTerminate)
		{
			JzSrvProcMsg(obj);
			sTimerSleep(100, NULL);
		}
	}

	//fade时,不保存文件
	if( !fade_record )
	{
		fade_len = (task->ASamplerate * task->AChannels * sizeof(short) * RECODE_SKIP_LEN) / 1000;
		if( task->MediaType == AK_REC_TYPE_WAVE)
		{
			// 录音结束,写入头/尾信息
			JzCbFileSeek(vfile, 0, SEEK_SET);
			WaveFileHead.file_size = recsize + sizeof(WaveFileHead) - 8;
			WaveFileHead.data_length = recsize;
			JzCbFileWrite(&WaveFileHead, sizeof(WAVE_HEADER),1,vfile);

			if( vfile->PlayLength > (fade_len + sizeof(WaveFileHead)) && fade_len )
			{
				fade_buf = (BYTE*)kmalloc(fade_len);
				kmemset(fade_buf,0,fade_len);
				JzCbFileSeek(vfile, recsize + sizeof(WaveFileHead) - fade_len , SEEK_SET);
				JzCbFileWrite(fade_buf, fade_len,1,vfile);
				kfree(fade_buf);
				kdebug(mod_audio, PRINT_INFO, "recode fade: skip wav len = %d\n",fade_len);
			}
		}
		else
		{
			if( vfile->PlayLength > fade_len && fade_len )
			{
				fade_buf = (BYTE*)kmalloc(fade_len);
				kmemset(fade_buf,0,fade_len);
				JzCbFileSeek(vfile, recsize - fade_len, SEEK_SET);
				JzCbFileWrite(fade_buf, fade_len,1,vfile);
				kfree(fade_buf);
				kdebug(mod_audio, PRINT_INFO, "recode fade: skip pcm len = %d\n",fade_len);
			}
		}

	}
	JzCbFileWriteFlush(vfile);
	fRecodeWav = 0;
	
	// 线程结束, 关闭文件和设备
	AdcClose(obj->hDac);

	// 设置线程结束标志	
	if(obj->bTerminate || (obj->bClose == 2))
	{	
		msgid = WM_MEDIA_TERMINATE;
		msg.MsgId = msgid;
		msg.hWnd = task->hWnd;
	}
	else if(obj->bClose)
	{	
		msgid = WM_MEDIA_CLOSE;
		msg.MsgId = msgid;
		msg.hWnd = task->hWnd;
	}
	else
	{
		// 非正常结束
		msgid = 0;
		*obj->bReady = -1;
	}
	
	// 设置返回消息参数	
	if(obj->bTerminate == 2)
		msg.Data.v = 1;
	else if(obj->bClose == 2)
		msg.Data.v = 2;
	else
		msg.Data.v = 0;
	
	// 删除对象
	if(obj->bTerminate == 1)
		obj_del = 0;
	else
		JzSrvDestroyNotify(task);
	
	// 发送WM_MEDIA_CLOSE消息
	if(msgid)
	{
		msg.hWndSrc = 0;
		msg.Param = 0;
	#if defined(STC_EXP)
		sGuiMsgPutMsg(&msg);
	#else
		GuiMsgPutMsg(&msg);
	#endif
	}

	if(buf_in)
		kfree(buf_in);
ThreadEnd:	
	// 设置线程结束标志	
	if(!obj_del)
		obj->bTerminate++;

#if defined(STC_EXP)
	sThreadTerminate(sThreadSelf());
#else
	ThreadTerminate(ThreadSelf());
#endif
}
Example #6
0
////////////////////////////////////////////////////
// 功能: 
// 输入: 
// 输出:
// 返回: 
// 说明: 
////////////////////////////////////////////////////
static void JzThreadPlayFile(DWORD p)
{
	PAK_VFILE vfile;
	PAK_OBJECT obj;
	PMEDIA_TASK task;
	VIDEO_PARAM video;
	MEDIALIB_STATUS player_status;
	MESSAGE msg;
	int cur_time;
	int duration;
	int msgid;
	int ret,jmp_ret;
	int max_wsize;
	int max_time;
	short *pcm,*pData;
	int fade,begin_time;
 	int obj_del = 1;
	int wlen;
	int block_num;
	int	time_out;
	DWORD init_start_time,init_end_time;

#ifdef MPLAYER_PRINTF_ENABEL
	syslog_set_global_level(PRINT_INFO);
#endif

	// 获取打开信息
	obj = (PAK_OBJECT)p;
	task = &obj->Task;
	vfile = &obj->File;
	init_start_time = TimerCount();
	kdebug(mod_audio, PRINT_INFO, "mplayer init player time = %d\n",init_start_time);
	obj->PlayerType = task->ExterdType;
#ifdef CONFIG_MAKE_BIOS
	task->ExterdType = 0;
#endif
	pcm          = NULL;
	obj->hDac    = NULL;
	video.hMutex = NULL;

	//初始化mplayer使用变量
	nMplayerDelay      = 0;
	nMplayerSamplerate = 0;
	nMplayerChannels   = 0;
	nMplayerAudioStart = 0;

	//初始化回调函数
	if( (ret = MediaLibInit(obj)) < 0 )
	{
		kdebug(mod_audio, PRINT_ERROR, "MediaLibInit failed\n");
		*obj->bReady = -1;
		if( ret != -2 )
			MediaLibClose(obj);
 		goto ThreadEnd;
	}
	kdebug(mod_audio, PRINT_INFO, "mplayer MediaLibInit end = %d\n",TimerCount());

	if( task->ExterdType )
	{
		//防止SD卡播放时,拔出SD卡,导致MPLAYER在初始化阶段死机
		obj->JzAvDecoder->fMplayerInit = 1;
		kdebug(mod_audio, PRINT_INFO, "set jump error addr\n");
		jmp_ret = ksetjmp(obj->JzAvDecoder->AudioJumpBuf);
		if( jmp_ret == 1 )
		{
			kdebug(mod_audio, PRINT_ERROR, "audio error, jump to end\n");
			*obj->bReady = -1;
			if( pcm )
				kfree(pcm);
			if( obj->hDac )
				DacClose(obj->hDac);
			if(video.hMutex)
				kMutexDestroy(video.hMutex);
			MediaLibClose(obj);
			goto ThreadEnd;
		}
	}

	//打开音频库
	if( MediaLibOpen(obj, 0) < 0 )
	{	//音频库打开失败
		kdebug(mod_audio, PRINT_ERROR, "MediaLibOpen failed\n");
		*obj->bReady = -1;
		MediaLibClose(obj);
 		goto ThreadEnd;
	}
	kdebug(mod_audio, PRINT_INFO, "mplayer MediaLibOpen end = %d\n",TimerCount());

	//得到音频库信息
	if( MediaLibGetInfo(obj) < 0 )
	{	//得到音频库信息失败
		kdebug(mod_audio, PRINT_ERROR, "MediaLibGetInfo failed\n");
		*obj->bReady = -1;
		MediaLibClose(obj);
 		goto ThreadEnd;
	}

	if( !obj->Info.bHasAudio  )
	{	//没有音频数据,直接退出
		*obj->bReady = -1;
		MediaLibClose(obj);
 		goto ThreadEnd;
	}

	if(obj->Info.bHasVideo)
	{
		//有视频,但是播放区域为空,直接退出(MP3里面播放改名的RMVB等。。。。)
		if( !(task->ShowRect.w  && task->ShowRect.h) )
		{
			*obj->bReady = -1;
			MediaLibClose(obj);
 			goto ThreadEnd;
		}
	}
	kdebug(mod_audio, PRINT_INFO, "mplayer MediaLibGetInfo end = %d\n",TimerCount());

	if( obj->PlayerType )
	{	//设置视频的显示区域以及位置
		if( task->ShowRect.w  && task->ShowRect.h )
			MplayerResizeVideo(obj,task);
		else
		{
			kdebug(mod_audio, PRINT_WARNING, "can't play video\n");
			obj->JzAvDecoder->fIpuEnable = 1;
		}
	}
	else
	{
		obj->StartTime = task->ShowRect.x;
		obj->EndTime   = task->ShowRect.y;
	}

	//申请播放PCM的内存
	block_num = MAX_PCM_GET_LEN;
	pcm = (short*)kmalloc(block_num);
	if( pcm == NULL )
	{
		kdebug(mod_audio, PRINT_ERROR, "memory lose pcm == null\n");
		*obj->bReady = -1;
		MediaLibClose(obj);
		goto ThreadEnd;
	}
	kdebug(mod_audio, PRINT_INFO, "mplayer kmalloc pcm end = %d\n",TimerCount());

	//MPLAYER播放器使用,用来设置从MPLAYER读到的PCM数据以及长度
	if( obj->PlayerType )
	{	//外部播放器使用变量
		pMediaPcmData = (BYTE*)pcm;
		nMediaPcmLen  = 0;
	}

	// 打开DAC设备,并设置DAC设备采样率、声道
	*obj->bReady = 1;
	obj->hDac = DacOpen();
	if(obj->hDac == NULL)
	{
		kdebug(mod_audio, PRINT_ERROR, "dac open error\n");
		kfree(pcm);
		MediaLibClose(obj);
		goto ThreadEnd;
	}
	if(DacSetSamplerate(obj->hDac, obj->Info.AudioSamplerate, obj->Info.AudioChannels) < 0)
	{
		kdebug(mod_audio, PRINT_ERROR, "set samplerate error\n");
		kfree(pcm);
		DacClose(obj->hDac);
		MediaLibClose(obj);
		goto ThreadEnd;
	}

	kdebug(mod_audio, PRINT_INFO, "mplayer dacopen end = %d\n",TimerCount());
	DacSetTempo(obj->hDac, obj->Task.Tempo);
	DacSetVolume(obj->hDac, obj->Task.Volume);
	kdebug(mod_audio, PRINT_INFO, "volume = %d, tempo=%d\n",obj->Task.Volume, obj->Task.Tempo);


	// 计算每次写入PCM数据最大值(1K的整数倍)
	max_wsize =  50 * (obj->Info.AudioSamplerate * obj->Info.AudioChannels * sizeof(short)) / 1000;
	max_wsize = ((max_wsize + 1023) / 1024) * 1024;
	max_time = (max_wsize * 1000) / (obj->Info.AudioSamplerate * obj->Info.AudioChannels * sizeof(short));

	begin_time = MediaLibPlay(obj);
	if( begin_time < 0 )
	{
		kdebug(mod_audio, PRINT_ERROR, "MediaLibPlay failed\n");
		if(video.hMutex)
			kMutexDestroy(video.hMutex);
		*obj->bReady = -1;
		DacClose(obj->hDac);
		MediaLibClose(obj);
		kfree(pcm);
		goto ThreadEnd;
	}

	// 设置视频输出
	if (obj->Info.bHasVideo)
	{
		// 启动视频解码线程
		video.obj = obj;
		video.fPlayVideo = 1;
		video.hMutex = kMutexCreate();
		video.audio_frame_time = 0;
		video.video_frame_time = 0;
		kdebug(mod_audio, PRINT_INFO, "create video thread\n");
		KernelThread(PRIO_USER+2, AkThreadVideoPlay, (DWORD)&video, 0x8000);
	}
	else
	{
		video.obj = obj;
		video.hMutex = NULL;
		video.fPlayVideo = 0;
		video.audio_frame_time = 0;
		video.video_frame_time = 0;
	}
		
	// 发送WM_MEDIA_OPEN消息
	if(task->hWnd)
	{
		msg.hWnd = task->hWnd;
		msg.Data.v = 0;
		msg.hWndSrc = 0;
		msg.MsgId = WM_MEDIA_OPEN;
		msg.Param = 0;
#if defined(STC_EXP)
		sGuiMsgPutMsg(&msg);
#else
		GuiMsgPutMsg(&msg);
#endif
	}

	// 循环解压并播放
	fade = 0;
	duration = 0;
	fPlayMedia = 1;
	obj->RecDuration = 0;

	if( task->ExterdType )
		obj->JzAvDecoder->fMplayerInit = 0;
	init_end_time = TimerCount();
	kdebug(mod_audio, PRINT_INFO, "mplayer start play time = %d\n",init_end_time);
	kdebug(mod_audio, PRINT_INFO, "playe init time = %dms\n",(init_end_time-init_start_time)*10);
	kdebug(mod_audio,PRINT_INFO,"obj->StartTime = %d, Obj->EndTime = %d\n",obj->StartTime,obj->EndTime);
	while(!obj->bClose && !obj->bTerminate)
	{
		// 解码音频数据
		if(video.hMutex)
			kMutexWait(video.hMutex);

		//得到PCM数据
		player_status = MediaLibGetStatus(obj);
		wlen = MediaLibGetPcm(obj,(BYTE*)pcm,block_num);
//		kprintf("wlen = %d\n",wlen);
		if((wlen<0) || (player_status==MEDIALIB_END) || (player_status==MEDIALIB_ERR))
		{
			DacWriteEnd(obj->hDac, 0);
			if(MEDIALIB_ERR == player_status)
			{
				kdebug(mod_media, PRINT_ERROR, "media lib error!\n");
				obj->bClose = 2;
			}
			else
				obj->bClose = 1;
			if(video.hMutex)
				kMutexRelease(video.hMutex);
			kdebug(mod_audio, PRINT_INFO, "wlen = %d, player_status = %d\n",wlen,player_status);
			break;
		}

		// 获取当前音频解码时间
		cur_time = MediaLibGetAudioCurTime(obj);
//		kprintf("cur time = %d\n",cur_time);
		if( obj->StartTime )
		{
			MediaLibSeek(obj,obj->StartTime);
			obj->StartTime = 0;
			wlen = 0;
		}

		if( obj->EndTime && cur_time >= obj->EndTime )
		{	//定时播放,如果播放时间到,则直接播放结束
			DacWriteEnd(obj->hDac, 0);
			obj->bClose = 1;
			if(video.hMutex)
				kMutexRelease(video.hMutex);
			kprintf("play seek end: cur time = %d, end time = %d\n",cur_time,obj->EndTime);
			break;
		}

		if(video.hMutex)
			kMutexRelease(video.hMutex);

		if( nMplayerAudioStart == 0 && video.hMutex)
		{
			time_out = 100;
			nMplayerAudioStart = 1;
			while( nMplayerAudioStart != 3 && time_out--)
				sTimerSleep(10,NULL);
			if( !time_out )
				kprintf("!!!!!!!! WARNNING : wait video time out !!!!!!!!\n");
			nMplayerAudioStart = 4;
		}

		// 输出音频数据到DA
		pData = pcm;
		obj->RecDuration = cur_time;
 		while(wlen > 0)
		{
			DWORD wsize;
			int ctl_code;

			// 写入PCM数据到DAC设备
			wsize = (wlen > max_wsize) ? max_wsize : wlen;
			if(fade)
			{
				int s;
				short pcms;
				pcms = wsize / sizeof(short);
				for(s=0; s<pcms; s++)
				{
					int tmp;
					tmp = (int)pData[s];
					tmp = (tmp * (pcms - s)) / pcms;
					pData[s] = (short)tmp;
				}
				DacWrite(obj->hDac, pData, wsize);
				DacWriteEnd(obj->hDac, 0);
				break;
			}
			else
			{
				if( DacWrite(obj->hDac, pData, wsize) == 0 )
				{	//出错,返回值为0
					kdebug(mod_audio, PRINT_ERROR, "dac write is 0 \n");
					obj->bClose = 1;
					break;
				}
			}

			// 提高当前时间精度
			if( wsize == max_wsize )
				obj->RecDuration += max_time;
			else
				obj->RecDuration += (wsize * 1000) / (obj->Info.AudioSamplerate * obj->Info.AudioChannels * sizeof(short));

			pData += wsize / sizeof(short);
			wlen -= wsize;
			
			// 控制动作处理
			if(video.hMutex)
				kMutexWait(video.hMutex);
			ctl_code = JzSrvProcMsg(obj);
			player_status = MediaLibGetStatus(obj);
			if(video.hMutex)
				kMutexRelease(video.hMutex);

 			// 等待退出暂停状态
			while( MEDIALIB_PAUSE == player_status && !obj->bClose && !obj->bTerminate)
			{
				sTimerSleep(100, NULL);

				if(video.hMutex)
					kMutexWait(video.hMutex);
				ctl_code = JzSrvProcMsg(obj);
				player_status = MediaLibGetStatus(obj);
				if(video.hMutex)
					kMutexRelease(video.hMutex);
			}
			
			// 检查是否退出
			if(obj->bTerminate)
			{
// 				if(fade == 0 && wlen == 0)
// 				{
// 					wlen = MediaLibGetPcm(obj,(BYTE*)pcm,block_num);
// 					pData = pcm;
// 					if(wlen < 0)
// 					{
// 						wlen = 0;
// 					}
// 				}
				kdebug(mod_audio, PRINT_INFO, "fade len:%d\n", wlen);
				fade = 1;
			}
 		}
	}

	//如果是强行退出,则直接关闭MOS管,方式喀嚓声
	if( obj->bTerminate && GetDacChannel() <= 1 )
	{
		kdebug(mod_audio, PRINT_INFO, "terminate media, close mute mos\n");
	}

	init_start_time = TimerCount();
	kdebug(mod_audio, PRINT_INFO, "close meidia start : %d\n",init_start_time);

	// 是否用于视频的互斥量
	if(video.hMutex)
	{	//等待视频结束
		while( 1 )
		{
			if( !video.fPlayVideo )
				break;
			sTimerSleep(10, NULL);
		}
		kMutexDestroy(video.hMutex);
	}

	// 关闭DAC设备
	DacClose(obj->hDac);
	MediaLibClose(obj);
	kfree(pcm);

	init_end_time = TimerCount();
	kdebug(mod_audio, PRINT_INFO, "close meidia end : %d - %dms\n",init_end_time, (init_end_time - init_start_time)*10);
ThreadEnd:
	fPlayMedia = 0;
	WinClipMask(NULL);

	//MPLAYER播放器使用,用来设置从MPLAYER读到的PCM数据以及长度
	if( obj->PlayerType )
	{	//外部播放器使用变量
		pMediaPcmData = NULL;
		nMediaPcmLen  = 0;
	}

	// 设置线程结束标志	
	msgid = 0;
	if(obj->bTerminate || (obj->bClose == 2))
	{	
		msgid = WM_MEDIA_TERMINATE;
		msg.MsgId = msgid;
		msg.hWnd = task->hWnd;
	}
	else if(obj->bClose)
	{	
		msgid = WM_MEDIA_CLOSE;
		msg.MsgId = msgid;
		msg.hWnd = task->hWnd;
	}
	else
	{
		// 未启动播放即结束
		msgid = 0;
		*obj->bReady = -1;
	}
	
	// 设置返回消息参数	
	if((obj->bTerminate == 2))
		msg.Data.v = 1;
	else if(obj->bClose == 2)
		msg.Data.v = 2;
	else
		msg.Data.v = 0;
	
	// 删除对象
	if(obj->bTerminate == 1)
		obj_del = 0;
	else
		JzSrvDestroyNotify(task);
	
	// 发送WM_MEDIA_CLOSE消息
	if(msgid)
	{
		msg.hWndSrc = 0;
		msg.Param = 0;
	#if defined(STC_EXP)
		sGuiMsgPutMsg(&msg);
	#else
		GuiMsgPutMsg(&msg);
	#endif
	}
	
	// 增加Terminate标记,方便退出
	if(!obj_del)
		obj->bTerminate++;

	kdebug(mod_audio, PRINT_INFO, "medialib close finish\n");
#ifdef MPLAYER_PRINTF_ENABEL
	syslog_set_global_level(PRINT_NOTICE);
#endif
#if defined(STC_EXP)
	sThreadTerminate(sThreadSelf());
#else
	ThreadTerminate(ThreadSelf());
#endif
}
Example #7
0
////////////////////////////////////////////////////
// 功能: 
// 输入: 
// 输出:
// 返回: 
// 说明: 
////////////////////////////////////////////////////
static void AkThreadVideoPlay(DWORD p)
{
	PVIDEO_PARAM video = (PVIDEO_PARAM)p;
	PAK_OBJECT obj;
	DWORD pre_audio_time;
	DWORD audio_time;
	DWORD frame_time;
	DWORD delay_time;
	DWORD totle_time;
	DWORD totle_fps;
	RECT *show_rect;
	int pts;
	int pass_frame;
	MEDIALIB_STATUS player_status;
			
	frame_time = 0;
	audio_time = 0;
	pre_audio_time = 0;
	pass_frame = 0;
	delay_time = 0;
	totle_time = 0;
	totle_fps  = 0;
	video->fPlayVideo = 1;
	frame_time = TimerCount();
	obj = video->obj;
	MxuEnable();

	show_rect = &obj->Task.ShowRect;
	WinClipMask(show_rect);
	while(!obj->bClose && !obj->bTerminate)
	{
		kMutexWait(video->hMutex);

		if( !nMplayerAudioStart || nMplayerAudioStart == 3 )
		{
			kMutexRelease(video->hMutex);
			sTimerSleep(10, NULL);
			continue;
		}

		if( nMplayerAudioStart == 1 )
			nMplayerAudioStart = 2;

		// 获取音频时间	
		audio_time = obj->RecDuration;
		
		// 矫正同步时间
		{
			DWORD tick;
			tick = TimerCount();
			pts  = MediaLibGetYuv(obj);
			totle_time += TimerCount() - tick;
			totle_fps++;
		}

		if( nMplayerAudioStart == 2 )
			nMplayerAudioStart = 3;
		
//		kprintf("%d,%d\n",pts,audio_time);
		if(pts < 0)
		{
			player_status = MediaLibGetStatus(obj);
			if (MEDIALIB_ERR == player_status)
			{
				kdebug(mod_video, PRINT_ERROR, "video decode error!\n");
				obj->bClose = 2;
				kMutexRelease(video->hMutex);
				break;
			}
			else if(MEDIALIB_PAUSE == player_status)
			{
				kMutexRelease(video->hMutex);
				
				// 等待退出暂停状态
				do
				{
					sTimerSleep(100, NULL);
					kMutexWait(video->hMutex);
					player_status = MediaLibGetStatus(obj);
					kMutexRelease(video->hMutex);
				}while((MEDIALIB_PAUSE == player_status) && !obj->bClose && !obj->bTerminate);
				
				// 重新设置系数				
				frame_time = 0;
				audio_time = 0;
				pre_audio_time = 0;
				frame_time = TimerCount();
				
				// 继续解压循环
				continue;
			}
			else
			{
				obj->bClose = 1;
				kMutexRelease(video->hMutex);
				break;
			}
		}
		player_status = MediaLibGetStatus(obj);
		if(player_status == MEDIALIB_ERR)
		{
			kdebug(mod_video, PRINT_ERROR, "video decode error!\n");
			obj->bClose = 2;
			kMutexRelease(video->hMutex);
			break;
		}

		kMutexRelease(video->hMutex);

		// 等待退出暂停状态
		while( MEDIALIB_PAUSE == player_status && !obj->bClose && !obj->bTerminate)
		{
			sTimerSleep(100, NULL);

			kMutexWait(video->hMutex);
			player_status = MediaLibGetStatus(obj);
			kMutexRelease(video->hMutex);
		}
	}
	WinClipMask(NULL);
	kdebug(mod_video, PRINT_INFO, "totle_fps = %d, total_time = %d\n",totle_fps,totle_time);
	kdebug(mod_video, PRINT_INFO, "video thread close\n");
	video->fPlayVideo = 0;
#if defined(STC_EXP)
	sThreadTerminate(sThreadSelf());
#else
	ThreadTerminate(ThreadSelf());
#endif
}
Example #8
0
////////////////////////////////////////////////////
// 功能: 
// 输入: 
// 输出:
// 返回: 
// 说明: 
////////////////////////////////////////////////////
static void JzThreadGetInfo(DWORD p)
{
 	PAK_VFILE vfile;
 	PAK_OBJECT obj;
	PMEDIA_TASK task;
	int ret;
	
	// 获取打开信息
 	obj = (PAK_OBJECT)p;
 	vfile = &obj->File;
	task = &obj->Task;
	vfile = &obj->File;
#ifdef CONFIG_MAKE_BIOS
	task->ExterdType = 0;
#endif
	obj->PlayerType = task->ExterdType;

	//初始化回调函数
	if((ret = MediaLibInit(obj)) < 0 )
	{
		kdebug(mod_media, PRINT_ERROR, "MediaLibInit failed.\n");
		*obj->bReady = -1;
		if( ret == -2 )
			goto ThreadEnd1;
		else
			goto ThreadEnd;
	}

	//打开音频库
	if( MediaLibOpen(obj, 1) < 0 )
	{	//音频库打开失败
		kdebug(mod_media, PRINT_ERROR, "MediaLibOpen failed.\n");
		*obj->bReady = -1;
 		goto ThreadEnd;
	}

	//得到音频库信息
	if( MediaLibGetInfo(obj) < 0 )
	{	//得到音频库信息失败
		kdebug(mod_media, PRINT_ERROR, "MediaLibGetInfo failed.\n");
		*obj->bReady = -1;
 		goto ThreadEnd;
	}
	if( obj->Info.bHasVideo )
	{	//视频文件,需要计算视频的显示尺寸
		SetVideoPosAndSize(obj,task);
	}
	obj->bGetInfo = 0;
	*obj->bReady = 1;
	
ThreadEnd:
	MediaLibClose(obj);
ThreadEnd1:

	// 设置线程结束标志	
	if(obj->bTerminate)
		obj->bTerminate++;

#if defined(STC_EXP)
	sThreadTerminate(sThreadSelf());
#else
	ThreadTerminate(ThreadSelf());
#endif
}
Example #9
0
static void *WriteRecordFileThread(void *arg)
{
	static unsigned int stopCount = 0;
	PCP_NODE_T *pRecPcp = NULL;
	int channel = (int)arg;
	time_t utc = 0;
	uint recordType = 0;
	uint writeSize = 0;
	uchar frameType = 0;
	RECORD_THREAD *p_rec = NULL;
	int recordCtlFlag = REC_SLEEP;
	int ret = 0;
    
	SVPrint("ch(%d) WriteRecordFileThread:%d!\r\n",channel,ThreadSelf());
	p_rec = &rec_thread[channel];
	while(p_rec->recordThreadRunFlag) 
    {    
    	recordCtlFlag = GetRecordCtlFlag(channel);
                    
    	switch(recordCtlFlag)
        {
        	case REC_START:    
            	stopCount = 0;
            	recordType = 0;
            	CloseRecLed(channel);
            	StartH264Stream(channel);
            	pRecPcp = RecordPoolRead( channel );
            	if( NULL == pRecPcp )
                {
                	RecordPoolWait( channel );
                }
            	else
                {
                	AnalysisFrameData( channel, pRecPcp, &utc, &recordType, 
                                                    &writeSize, &frameType );

                	FiPrint2( "wait I frame,frameType(%d)!\r\n",
                            	pRecPcp->pcpHead.type);
                	if( FI_FRAME_TYPE_VIDEO_I != pRecPcp->pcpHead.type )
                    {
                    	FiPrint2( "start record but no I frame(%d)!\r\n",
                                        	pRecPcp->pcpHead.type);
                    	RecordPoolFree( pRecPcp );
                    	continue;
                    }    
                	ret = CreateRecordAndIndexFile( channel, utc );
                	if(FI_SUCCESS == ret)
                    {
                    	ResetIndexStruct( channel );
                    	ret = WriteDataToDisk( channel, pRecPcp, writeSize, recordType, utc );
                    	if(FI_SUCCESS == ret)
                        {
                        	SetRecordCtlFlag( channel, REC_WRITE );
                        	OpenRecLed( channel );
                        }    
                    }
                	RecordPoolFree( pRecPcp );                    
                	if(FI_SUCCESS != ret)
                    {
                    	sleep(1);
                    }    
                }
            	break;
        	case REC_WRITE:    
            	RecordPoolWait( channel );
            	while( 1 )
                {
                	if( NULL == (pRecPcp=RecordPoolRead(channel)) )
                    {
                    	break;
                    }                    
                	AnalysisFrameData( channel, pRecPcp, &utc, &recordType, 
                                                    &writeSize, &frameType );
                	ret = WriteDataToDisk( channel, pRecPcp, writeSize, recordType, utc );
                	if( FI_SUCCESS != ret )
                    {
                    	SetRecordCtlFlag( channel, REC_START );
                    }
                	RecordPoolFree( pRecPcp );
                }                
            	break;
        	case REC_SWITCH:
            	stopCount = 0;
            	RecordPoolWait( channel );
            	while( 1 )
                {
                	if( NULL == (pRecPcp=RecordPoolRead(channel)) )
                    {
                    	break;
                    }
                	AnalysisFrameData( channel, pRecPcp, &utc, &recordType,
                                                &writeSize, &frameType );
                    
                	if( FI_FRAME_TYPE_VIDEO_I != pRecPcp->pcpHead.type )
                    {
                    	ret = WriteDataToDisk( channel, pRecPcp, writeSize, recordType, utc );
                    	if( FI_SUCCESS != ret )
                        {
                        	SetRecordCtlFlag( channel, REC_START );
                        }
                    }
                	else 
                    {    
                    	CloseRecordAndIndexFile( channel );
                    	utc = time( NULL );
                    	ret = CreateRecordAndIndexFile( channel, utc );                        
                    	if( FI_SUCCESS == ret )
                        {
                        	ResetIndexStruct( channel );
                        	ret = WriteDataToDisk( channel, pRecPcp, 
                                    	writeSize, recordType, utc );
                        	if( FI_SUCCESS == ret )
                            {
                            	SetRecordCtlFlag( channel, REC_WRITE );
                            }                            
                        }
                    	else //if(FI_SUCCESS != ret)
                        {
                        	SetRecordCtlFlag( channel, REC_START );
                        	Usleep(1000);
                        }    
                    }    
                	RecordPoolFree( pRecPcp );
                }                
            	break;
        	case REC_STOP:
            	while( 1 )
                {
                	pRecPcp = RecordPoolRead( channel );
                	SVPrint( "ql debug -ch(%d), pRecPcp(0x%X), stopCount(%u)!\r\n",
                        	channel, pRecPcp, stopCount );
                	if( NULL == pRecPcp ||
                        ++stopCount >= (MAX_RECORD_DATA_NODE << 1) )
                    {
                    	break; // while( 1 )
                    }
                	AnalysisFrameData( channel, pRecPcp, &utc, &recordType, 
                                                &writeSize, &frameType );
                	ret = WriteDataToDisk( channel, pRecPcp, writeSize, recordType, utc );
                	RecordPoolFree( pRecPcp );
                	if( FI_SUCCESS != ret )
                    {
                    	break; // while( 1 )
                    }                        
                }                
                
            	CloseRecordAndIndexFile( channel );
            	SetRecordCtlFlag( channel, REC_SLEEP );
            	CloseH264Stream( channel );
            	CloseRecLed( channel );
            	break;
        	case REC_SLEEP:
        	default:
            	Usleep( 500000 );
            	break;
        } //switch	        
    }    //while(1)    
	SVPrint("quit ch(%d) WriteRecordFileThread!\r\n",channel);
	return NULL;
}
Example #10
0
/*********************************************************
  录像监视线程,该线程与系统时间有关,
  请在启动应用线程后再启动该线程
  并在启动此次线程再启动录像线程
***********************************************************/
static void *ManageRecordThread(void *arg)
{
	int chNum = REAL_CHANNEL_NUM;
	int i,j;
	int real_time[chNum];
	int base_time[REAL_CHANNEL_NUM] = {-1};
	int real_year[chNum],real_month[chNum],real_day[chNum];
	int base_year[chNum],base_month[chNum],base_day[chNum];
	uint base_rec_type[REAL_CHANNEL_NUM];
	uint real_rec_type[REAL_CHANNEL_NUM];    
	int alarm_real_time[REAL_CHANNEL_NUM];
	int alarm_base_time[REAL_CHANNEL_NUM];    
	char real_parh[RECORD_FILENAME_LEN] = {0};
	char base_path[RECORD_FILENAME_LEN] = {0};

	SVPrint("start ManageRecordThread:%d!\r\n",ThreadSelf());
    
	while(rec_manage.recordManageRunFlag)
    {
    	FiRecStartAutoDelOldFile();
        /*录像分区改变切换文件,优先级最高*/
    	if(FI_FAIL == FiHddGetUsingPartition(real_parh))
        {
        	for(i=0;i<chNum;i++)
            {
            	if(REC_SLEEP != GetRecordCtlFlag(i))
                	SetRecordCtlFlag(i,REC_STOP);
            }
        	sleep(1);
        	continue;
        }
    	else
        {
        	if(0 != strcmp(base_path,real_parh))
            {
            	strcpy(base_path,real_parh);
            	for(i=0;i<chNum;i++)
                {
                	if(REC_WRITE == GetRecordCtlFlag(i))
                    {
                    	SVPrint("record switch partition.\r\n");    
                    	RefrechAlarmBaseTimeCursor(i);
                    	RefrechTimerBaseTimeCursor(&real_time[i],&real_year[i],&real_month[i],&real_day[i],
                                        &base_time[i],&base_year[i],&base_month[i],&base_day[i]);
                    	SetRecordCtlFlag(i,REC_SWITCH);    //仅仅录像分区,不做任何时间检测
                    }
                }
            }
        }
        
    	if(-1 == manage_init_flag)
        {            
            
        	for(j=0;j<chNum;j++)
            {
                /*初始化定时录像监测*/
            	real_time[j] = time(NULL);
            	base_time[j] = real_time[j];
            	FiTimeUtcToHuman(base_time[j],&base_year[j],&base_month[j],&base_day[j],NULL,NULL,NULL);

                /*初始化录像类型切换监测*/            
            	real_rec_type[j] = GetRecordType(j);
            	base_rec_type[j] = real_rec_type[j];

            	RefrechAlarmBaseTimeCursor(j);
            	alarm_real_time[j] = SysRunTimeGet();
            }
            
        	manage_init_flag = 0;
        }        
        
        /*监测手动和定时录像*/
    	for(i=0;i<chNum;i++)
        {
        	ManageHandRecord(i);
        	ManageTimerRecordTime(i);            
        }
        
        /*定时录像切文件*/
    	for(i=0;i<chNum;i++)
        {            
        	real_time[i] = time(NULL);
        	FiTimeUtcToHuman(real_time[i],&real_year[i],&real_month[i],&real_day[i],NULL,NULL,NULL);
        	if(( real_time[i] - base_time[i] >= FiRecGetRecFileSwitchTime() ) || 
                (real_time[i] - base_time[i] < 0 && base_time[i] - real_time[i] > RECORD_TIME_ERROR_RANGE)    || 
                (real_year[i] != base_year[i]) || (real_month[i] != base_month[i]) || (real_day[i] != base_day[i]))
            {
            	SVPrint("ch(%d),%d-%d=%d\r\n",i,real_time[i],base_time[i],real_time[i]-base_time[i]);    
            	RefrechAlarmBaseTimeCursor(i);
            	RefrechTimerBaseTimeCursor(&real_time[i],&real_year[i],&real_month[i],&real_day[i],
                                    &base_time[i],&base_year[i],&base_month[i],&base_day[i]);
            	if(REC_WRITE == GetRecordCtlFlag(i))
                {                        
                	SetRecordCtlFlag(i,REC_SWITCH);                    
                }    
            }
        } 
        /*报警录像情况的录像类型改变从而切换文件*/
    	for(i=0;i<chNum;i++)
        {
        	real_rec_type[i] = GetRecordType(i);            
        	if(real_rec_type[i] & RECORD_TYPE_ALARM_ALL)
            {                
            	alarm_base_time[i] = getAlarmBaseTimeCursor(i);
            	alarm_real_time[i] = SysRunTimeGet();
            	if( alarm_real_time[i] - alarm_base_time[i] >= FiRecGetRecFileSwitchTimeAlarm() )
                {
                	SVPrint("%d-%d=%d\r\n",alarm_real_time[i] , alarm_base_time[i],alarm_real_time[i] - alarm_base_time[i]);
                	FiRecStopRecord(i,RECORD_TYPE_ALARM_ALL);
                	RefrechAlarmBaseTimeCursor(i);                        
                	RefrechTimerBaseTimeCursor(&real_time[i],&real_year[i],&real_month[i],&real_day[i],
                                    &base_time[i],&base_year[i],&base_month[i],&base_day[i]);                
                	if(real_rec_type[i] & (RECORD_TYPE_ALL&(~RECORD_TYPE_ALARM_ALL)))                    
                    {
                    	SetRecordCtlFlag(i,REC_SWITCH);                            
                    }    
                }
            }            
        }	

        /* 控制录像线程启动录像 ,是否启动录像*/
    	for(i=0;i<chNum;i++)
        {
        	real_rec_type[i] = GetRecordType(i);
        	if(real_rec_type[i] & RECORD_TYPE_ALL)
            {
            	if(FI_TRUE == ControlRecordThreadStartRecord(i))
                {
                	RefrechAlarmBaseTimeCursor(i);                        
                	RefrechTimerBaseTimeCursor(&real_time[i],&real_year[i],&real_month[i],&real_day[i],
                                    &base_time[i],&base_year[i],&base_month[i],&base_day[i]);
                }
            }
        	else
            {
            	ControlRecordThreadStopRecord(i);
            }
        }    
        
    	Usleep(500000); //500ms
    }    //while(rec_manage.recordManageRunFlag)
    
	SVPrint("quit ManageRecordThread!\r\n");
    
	return NULL;
}