Ejemplo n.º 1
0
static int get_bit_raw(fsk_data *fskd, short *buffer, int *len)
{
	/* This function implements a DPLL to synchronize with the bits */
	float x,spb,spb2,ds;
	int f;

	spb = fskd->spb; 
	if (fskd->spb == 7)
		spb = 8000.0 / 1200.0;
	ds = spb/32.;
	spb2 = spb/2.;

	for (f = 0;;) {
		if (demodulator(fskd, &x, GET_SAMPLE))
			return -1;
		if ((x * fskd->x0) < 0) {	/* Transition */
			if (!f) {
				if (fskd->cont<(spb2))
					fskd->cont += ds;
				else
					fskd->cont -= ds;
				f = 1;
			}
		}
		fskd->x0 = x;
		fskd->cont += 1.;
		if (fskd->cont > spb) {
			fskd->cont -= spb;
			break;
		}
	}
	f = (x > 0) ? 0x80 : 0;
	return f;
}
Ejemplo n.º 2
0
// 文件测试接收
void File_Rx()
{
	av_register_all();

    boost::coroutines::asymmetric_coroutine<float>::push_type demodulator(FSK_demodulator<CHIPSIZE/2,CHIPSIZE, SAMPLES_PER_CHIP>);

    AVFormatContext * avcontext = avformat_alloc_context();

    if(avformat_open_input(&avcontext, "test.wav", NULL, NULL))
    {
        std::cerr << "can't open test.wav" << std::endl;
        exit(0);
    }

    if( avformat_find_stream_info(avcontext, NULL) )
    {
        std::cerr << "can't guess test.wav file format" << std::endl;
        exit(0);
    }

    AVCodec * decoder = NULL;
	int audio_stream_index = av_find_best_stream(avcontext, AVMEDIA_TYPE_AUDIO, -1, -1, &decoder, 0);

    if( avcodec_open2(avcontext->streams[audio_stream_index]->codec, decoder, NULL) )
    {
        std::cerr << "avcodec_open2 failed" << std::endl;
        exit(0);
    }

	// 循环读取
    while(true)
    {
		AVPacket packet = { 0 };
		av_init_packet(&packet);
		BOOST_SCOPE_EXIT_ALL(&packet)
		{
			av_free_packet(&packet);
		};

		// finished
		if( av_read_frame(avcontext, &packet) < 0 )
		{
			std::cerr << "file EOF" << std::endl;
			break;
		}

		if( packet.stream_index != audio_stream_index)
			continue;

		AVFrame * avframe = av_frame_alloc();
		BOOST_SCOPE_EXIT_ALL(&avframe)
		{
			av_frame_free(&avframe);
		};

		while(1)
		{
			int got_frame = 0;
			int ret = avcodec_decode_audio4(avcontext->streams[audio_stream_index]->codec, avframe, &got_frame, &packet);
			if( ret < 0 )
			{
				std::cerr << "error decoding audio file" << std::endl;
				exit(1);
			}

			packet.size -= ret;
			packet.data += ret;
			if (!got_frame && packet.size > 0)
				continue;

			/* packet中已经没有数据了, 并且不足一个帧, 丢弃这个音频packet. */
			if (packet.size == 0 && !got_frame)
				break;

			if (avframe->linesize[0] != 0)
			{
				// 传递给流水线下一步
				for(int i=0; i < av_samples_get_buffer_size(NULL,
					avcontext->streams[audio_stream_index]->codec->channels, avframe->nb_samples,
						avcontext->streams[audio_stream_index]->codec->sample_fmt,1) ; i+=2)
				{
					// 丢掉一个频道
					demodulator( avframe->data[0][i] / 32768.0 );
				}
			}
		}
	}

    for(int i=0; i < avcontext->nb_streams; i ++)
    {
        if(avcontext->streams[i]->codec)
            avcodec_close(avcontext->streams[i]->codec);
    }

    avformat_close_input(&avcontext);
    // RAII 自动关闭了
}
Ejemplo n.º 3
0
int fsk_serial(fsk_data *fskd, short *buffer, int *len, int *outbyte)
{
	int a;
	int i,j,n1,r;
	int samples = 0;
	int olen;

	switch (fskd->state) {
		/* Pick up where we left off */
	case STATE_SEARCH_STARTBIT2:
		goto search_startbit2;
	case STATE_SEARCH_STARTBIT3:
		goto search_startbit3;
	case STATE_GET_BYTE:
		goto getbyte;
	}
	/* We await for start bit	*/
	do {
		/* this was jesus's nice, reasonable, working (at least with RTTY) code
		to look for the beginning of the start bit. Unfortunately, since TTY/TDD's
		just start sending a start bit with nothing preceding it at the beginning
		of a transmission (what a LOSING design), we cant do it this elegantly */
		/*
		if (demodulator(zap,&x1)) return(-1);
		for (;;) {
			if (demodulator(zap,&x2)) return(-1);
			if (x1>0 && x2<0) break;
			x1 = x2;
		}
		*/
		/* this is now the imprecise, losing, but functional code to detect the
		beginning of a start bit in the TDD sceanario. It just looks for sufficient
		level to maybe, perhaps, guess, maybe that its maybe the beginning of
		a start bit, perhaps. This whole thing stinks! */
		if (demodulator(fskd, &fskd->x1, GET_SAMPLE))
			return -1;
		samples++;
		for (;;) {
search_startbit2:		   
			if (*len <= 0) {
				fskd->state  =  STATE_SEARCH_STARTBIT2;
				return 0;
			}
			samples++;
			if (demodulator(fskd, &fskd->x2, GET_SAMPLE))
				return(-1);
#if 0
			printf("x2  =  %5.5f ", fskd->x2);
#endif			
			if (fskd->x2 < -0.5)
				break; 
		}
search_startbit3:		   
		/* We await for 0.5 bits before using DPLL */
		i = fskd->spb/2;
		if (*len < i) {
			fskd->state = STATE_SEARCH_STARTBIT3;
			return 0;
		}
		for (; i>0; i--) {
			if (demodulator(fskd, &fskd->x1, GET_SAMPLE))
				return(-1); 
#if 0
			printf("x1 = %5.5f ", fskd->x1);
#endif			
			samples++;
		}

  		/* x1 must be negative (start bit confirmation) */

	} while (fskd->x1 > 0);
	fskd->state = STATE_GET_BYTE;

getbyte:

	/* Need at least 80 samples (for 1200) or
		1320 (for 45.5) to be sure we'll have a byte */
	if (fskd->nbit < 8) {
		if (*len < 1320)
			return 0;
	} else {
		if (*len < 80)
			return 0;
	}
	/* Now we read the data bits */
	j = fskd->nbit;
	for (a = n1 = 0; j; j--) {
		olen = *len;
		i = get_bit_raw(fskd, buffer, len);
		buffer += (olen - *len);
		if (i == -1)
			return(-1);
		if (i)
			n1++;
		a >>= 1;
		a |= i;
	}
	j = 8-fskd->nbit;
	a >>= j;

	/* We read parity bit (if exists) and check parity */
	if (fskd->parity) {
		olen = *len;
		i = get_bit_raw(fskd, buffer, len); 
		buffer += (olen - *len);
		if (i == -1)
			return(-1);
		if (i)
			n1++;
		if (fskd->parity == 1) {	/* parity=1 (even) */
			if (n1&1)
				a |= 0x100;		/* error */
		} else {			/* parity=2 (odd) */
			if (!(n1&1))
				a |= 0x100;	/* error */
		}
	}
	
	/* We read STOP bits. All of them must be 1 */
	
	for (j = fskd->nstop;j;j--) {
		r = get_bit_raw(fskd, buffer, len);
		if (r == -1)
			return(-1);
		if (!r)
			a |= 0x200;
	}

	/* And finally we return  */
	/* Bit 8 : Parity error */
	/* Bit 9 : Framming error*/

	*outbyte = a;
	fskd->state = STATE_SEARCH_STARTBIT;
	return 1;
}