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

📄 framebuffer.c

📁 本程序为ST公司开发的源代码
💻 C
字号:
/************************************************** * * buffer.c * * CVS ID:   $Id: framebuffer.c,v 1.35 2007/09/21 05:26:11 hara Exp $ * Author:   Raffaele Belardi [RB] - STM) * Date:     $Date: 2007/09/21 05:26:11 $ * Revision: $Revision: 1.35 $ *  * Description: *  * API for FrameBuffer access *  *************************************************** *  * COPYRIGHT (C) ST Microelectronics  2005 *            All Rights Reserved * **************************************************** * * STM CVS Log: * * $Log: framebuffer.c,v $ * Revision 1.35  2007/09/21 05:26:11  hara * Initial implementation for WMDRM feature into A+. * * Revision 1.34  2006/12/05 17:49:21  belardi * Removed unused variable * * Revision 1.33  2006/12/04 16:53:22  chlapik * FB handling modified: * - always ask max 1 element * - startOffset modify only if there are non zero amount of data * - subcode or - ed if element was once filled * * Revision 1.32  2006/10/17 09:51:20  trubac * FB init bug fixed * * Revision 1.31  2006/09/27 19:48:59  belardi * Removed (global) unused variables * * Revision 1.30  2006/09/18 09:55:21  belardi * Corrected CVS keyword usage * * Revision 1.29  2006/09/18 09:23:02  belardi * Added Log CVS keyword into file header * * ***************************************************/#include "gendef.h"#include "osal.h"//#include "wmadefs.h"#include "decoder_task.h"#include "controller.h"#include "framebuffer.h"#include "tag_defs.h" // [RB] for MAX_STRINGS_SIZE		//[LL] id3tag_defs.h moved#include "xfile.h"#include <string.h> // memset,...//int cc = 0; //ok - testuint32 decoderReadBytes;     // number of read (acquired by decoder) bytes in current fileuint32 decoderDecodedBytes;  // number of decoded bytes in current file#ifdef BITSTREAM_ARRAY		//#include "input3.h" //O.K. input WMA bitstream	//#include "input_16_16_long.h"	#include "input.h" //mp3	unsigned long long g_current_read; //O.K. - where to read from input bitstream buffer#endifunsigned char g_FB_writeTo; // FrameBuffer Element # to be filled inunsigned char g_FB_readFrom; // Lastly read out FrameBuffer Element #int g_FBempty; // number of empty elements in FB#if (0 != HAVE_WMDRM_LARGE_BUFFER)FrameBufferElement FrameBuffer[FrameBufferSdramElements+1];  /* FrameBufferSdramElements : Big elements number for FrameBuffer in SDRAM */uint16 FrameBufferElements = FrameBufferInternalElements;unsigned char FrameBufferDataBuffer[FRAME_BUFFER_ELEMENT_LENGTH*(FrameBufferInternalElements) + MAX_DATA_REQUESTED];#elseFrameBufferElement FrameBuffer[FrameBufferElements+1];unsigned char FrameBufferDataBuffer[FRAME_BUFFER_ELEMENT_LENGTH*(FrameBufferElements) + MAX_DATA_REQUESTED];#endif/*************************************************** * FrameBufferInit() * * *************************************************/void FrameBufferInit(uint32 sz){	uint8 i;	// Create the buffers of dimension multiple of 4 to limit	// alignment problems in DMA	//uint32 req_dim = (sz*(FrameBufferElements) + MAX_DATA_REQUESTED) & 0xFFFFFFFC;	//req_dim += 4;			// & !!! should be there ???		// memset((char *) &(FrameBuffer), 0, sizeof(FrameBufferElement) * (FrameBufferElements+1) );			//tmpP = (int *) malloc(req_dim); // 32 bit aligned	//Data = (unsigned char *) tmpP;	#if (0 != HAVE_WMDRM_LARGE_BUFFER)    FrameBufferElements = FrameBufferInternalElements;#endif	g_FB_writeTo = 1;	g_FB_readFrom = 0;	g_FBempty = FrameBufferElements;		FrameBuffer[0].en = 0; 	FrameBuffer[0].status = fbEmpty;	FrameBuffer[0].data = FrameBufferDataBuffer;		for (i = 1; i < FrameBufferElements + 1; i++) {				FrameBuffer[i].en = i; 		FrameBuffer[i].status = fbEmpty;		FrameBuffer[i].data = FrameBufferDataBuffer + MAX_DATA_REQUESTED + (i - 1)*FRAME_BUFFER_ELEMENT_LENGTH; //to guarantee continuos buffer		//FrameBuffer[i].data = (char *) pseudoMalloc(req_dim);	}	}			#if (0 != HAVE_WMDRM_LARGE_BUFFER)/*************************************************** * FrameBufferSdramInit() * * *************************************************/void FrameBufferSdramInit(uint32 sz){	uint8 i;                uint8 *pFrameBufferDataBuffer;	    FrameBufferElements = FrameBufferSdramElements;    pFrameBufferDataBuffer = cap_input_buffer_SDRAM;	g_FB_writeTo = 1;	g_FB_readFrom = 0;	g_FBempty = FrameBufferSdramElements;		FrameBuffer[0].en = 0; 	FrameBuffer[0].status = fbEmpty;	FrameBuffer[0].data = pFrameBufferDataBuffer; /* Re-use shockproof buffer for Big Frame buffer. */    		for (i = 1; i < FrameBufferSdramElements + 1; i++) {				FrameBuffer[i].en = i; 		FrameBuffer[i].status = fbEmpty;           		FrameBuffer[i].data = pFrameBufferDataBuffer + MAX_DATA_REQUESTED + (i - 1)*FRAME_BUFFER_ELEMENT_LENGTH; //to guarantee continuos buffer	}	}		#endif/*************************************************** * FrameBufferStartTransfer() * * Programs DMA to copy data from the CHANNEL_ITF into the  * FrameBuffer.  *  * *************************************************//* void FrameBufferStartTransfer(ElementFlagType FBflag, FILE_STRUCT *File, FAT_PRIVATE_STRUCT *FAT_private){		int copiedDataLength;	int i;	ElementFlagType FBflag2 = FBflag;#ifdef BITSTREAM_ARRAY		for(i=0;i<FRAME_BUFFER_ELEMENT_LENGTH;i++)		(FrameBuffer[g_FB_writeTo].data)[i] =  (g_bitstream + g_current_read)[i];	//memmove(FrameBuffer[g_FB_writeTo].data, g_bitstream + g_current_read, FRAME_BUFFER_ELEMENT_LENGTH);			g_current_read += FRAME_BUFFER_ELEMENT_LENGTH;	copiedDataLength = FRAME_BUFFER_ELEMENT_LENGTH;	#endif#ifdef FS_ARRAY	if (cc == 47)		cc++; 	copiedDataLength = FileRead_FAT(FAT_private,File,FrameBuffer[g_FB_writeTo].data,FRAME_BUFFER_ELEMENT_LENGTH,0);		if (copiedDataLength < FRAME_BUFFER_ELEMENT_LENGTH)	{		FBflag2 = last;		if (copiedDataLength < 0) copiedDataLength = 0;	}#endif			FrameBuffer[g_FB_writeTo].status = fbTransferInProgress;		{			// Following part of the code should be executed		// after successful filling of FrameBuffer (i.e. after DMA transfer)	}		FrameBuffer[g_FB_writeTo].ElementFlag = FBflag2;	FrameBufferTransferDone(copiedDataLength);} *//*************************************************** * FrameBufferTransferDone() * * Sets flags after DMA transfer is done.  * Called from DMA interrupt   *  * *************************************************//* void FrameBufferTransferDone(int copiedDataLength){	g_FBempty--; 							// decrement number of empty elements	FrameBuffer[g_FB_writeTo].availableDataLength = copiedDataLength;	FrameBuffer[g_FB_writeTo].status = 3; 	// fbTransferComplete;		FrameBuffer[g_FB_writeTo].EndOfFile = cc++;} *//*************************************************** * FillFrameBuffer() * * Provides data from FB to Decoder (if data are ready) *  * *************************************************/FrameBufferStatus FrameBufferGetData(FrameBufferElement *pBufferElement, uint8 update){		unsigned char tmp_readFrom = (g_FB_readFrom%FrameBufferElements) + 1;		if (FrameBuffer[tmp_readFrom].status == fbDataReady)	{		*pBufferElement = FrameBuffer[tmp_readFrom];		if (update)		{			g_FB_readFrom = tmp_readFrom;			decoderReadBytes = FrameBuffer[tmp_readFrom].startOffset;		}			return fbDataReady;	}	else	{		return fbEmpty; // ? fbTransferInProgress	}	}/*************************************************** *  * SetEmptyFBE() * * Sets FB Elements as fbEmpty *  * *************************************************/void SetEmptyFBE(unsigned char From, unsigned char To){	unsigned char c;		for (c = From; c != To; c ++) //= (c%FrameBufferElements)+1)	{		//FrameBuffer[c].ElementFlag = FT_MIDDLE;		if(FrameBuffer[c].status != fbEmpty)		{		  FrameBuffer[c].status = fbEmpty;		  g_FBempty++;		}	}		if (g_FBempty > FrameBufferElements)	{	  g_FBempty = FrameBufferElements;	}	if ((g_FBempty > FB_EMPTY_RATIO) && (!decoderStopRequest()))	{		// request new data from controller		event_req_set_decoder(READY);		//controller_update_status(CONTROLLER_NEW_DECODER_DATA_REQUEST_EVENT);	}			}/*************************************************** *  * SetEmptyFBECycle() * * Sets FB Elements as fbEmpty in Circular buffer * * Clears both From and To including (!) *  * *************************************************/void SetEmptyFBECycle(unsigned char From, unsigned char To){	unsigned char c;	if (To == 0)	{		To = FrameBufferElements;	}	for (c = From; c != To; c = (c%FrameBufferElements)+1)	{		if(FrameBuffer[c].status != fbEmpty)		{		  FrameBuffer[c].status = fbEmpty;		  g_FBempty++;		}		FrameBuffer[c].ElementFlag = FT_MIDDLE;	}		if(FrameBuffer[c].status != fbEmpty)	{	  FrameBuffer[c].status = fbEmpty;	  g_FBempty++;	}	FrameBuffer[c].ElementFlag = FT_MIDDLE;		if (g_FBempty > FrameBufferElements)	{	  g_FBempty = FrameBufferElements;	}				if ((g_FBempty > FB_EMPTY_RATIO) && (!decoderStopRequest()))	{		// request new data from controller		event_req_set_decoder(READY);		//controller_update_status(CONTROLLER_NEW_DECODER_DATA_REQUEST_EVENT);#if (1 == HAVE_WMDRM)           /* To perform Frame Buffer filling as soon as possible, after 1 frame buffer element is empty. */        event_out_shedule(DECODER_REQ_EVENT);  #endif	}		}/*************************************************** *  * GetElementNumber() * * According to *pBuffer sets ElementNumber * If 0 then return 1 *  * *************************************************/unsigned char GetElementNumber(unsigned char *pBuffer){	int element;	if (pBuffer < (FrameBuffer[2].data))		element = 1;	else		element = 1 + ((pBuffer - (FrameBuffer[1].data)) / FRAME_BUFFER_ELEMENT_LENGTH);	return element;}/*void SetEmptyAllFBE(void){	int i;	for (i = 1; i < FrameBufferElements + 1; i++) {				FrameBuffer[i].status = fbEmpty;	}}*//*************************************************** *  * GetNextFBElement() * *  * *************************************************/#if 0 // [RB] commente out to reduce ROM spaceunsigned char *GetNextFBElement(void){	return (FrameBuffer[(g_FB_readFrom%FrameBufferElements) + 1].data);}#endifuint8* FBM_GetFreeElement(uint16 *bytes_free){	uint8* ret = NULL;		if (FrameBuffer[g_FB_writeTo].status == fbEmpty)	{		ret = FrameBuffer[g_FB_writeTo].data;		*bytes_free = FRAME_BUFFER_ELEMENT_LENGTH;			if (FrameBuffer[g_FB_writeTo].ElementFlag & FT_UNFINISHED)		{			ret += FrameBuffer[g_FB_writeTo].availableDataLength; // update destination pointer			*bytes_free -= FrameBuffer[g_FB_writeTo].availableDataLength;		}		}		return ret;	}void FBM_SetFullElement(tQsubcode_event *subcode, ElementFlagType FBflag_last, uint16 copiedDataLength, uint32 startOffset){	uint16 copiedBytes;	copiedBytes = copiedDataLength;			if (FrameBuffer[g_FB_writeTo].ElementFlag & FT_UNFINISHED)	{		copiedBytes += 	FrameBuffer[g_FB_writeTo].availableDataLength;		FrameBuffer[g_FB_writeTo].ElementFlag &= ~FT_UNFINISHED;	}				if ((copiedBytes > 0) || (!copiedDataLength))	{		FrameBuffer[g_FB_writeTo].ElementFlag = FBflag_last;			FrameBuffer[g_FB_writeTo].availableDataLength = copiedBytes;				//handling of startOffset		if(copiedDataLength)		{ //if some data provided, update startOffset		  FrameBuffer[g_FB_writeTo].startOffset = startOffset; // set offset from the begining of song		}		else		{ //no data provided		  if(!copiedBytes)		  { //last element is full, next one will be empty		    FrameBuffer[g_FB_writeTo].startOffset = 0;		  }		}                //handling of subcode        if(copiedDataLength)        { //only if some data provided		  if (subcode != NULL)		  { //if subcode exists		    if(copiedBytes == copiedDataLength)		    { //we fill this element first time		      FrameBuffer[g_FB_writeTo].subcode = *subcode;			    }		    else		    { //we fill this element not first time		      (FrameBuffer[g_FB_writeTo].subcode.event_type) |= (subcode->event_type);			    }          }        }				if ((FBflag_last == FT_LAST) || (FBflag_last == FT_FSLAST))		{			FrameBuffer[g_FB_writeTo].status = fbDataReady;			g_FBempty--; 							// decrement number of empty elements			g_FB_writeTo = (g_FB_writeTo%FrameBufferElements) + 1;			}		else			{			if (copiedBytes == FRAME_BUFFER_ELEMENT_LENGTH)			{				FrameBuffer[g_FB_writeTo].status = fbDataReady;				g_FBempty--; 							// decrement number of empty elements				g_FB_writeTo = (g_FB_writeTo%FrameBufferElements) + 1;			}			else			{				FrameBuffer[g_FB_writeTo].ElementFlag |= FT_UNFINISHED;				}		}	}	}uint32 GetDecodedBytes(void){	return decoderDecodedBytes;}void SetDecodedBytes(uint32 unprocessedData){	decoderDecodedBytes = decoderReadBytes - unprocessedData;}	void SetDecodedBytesWMA(uint32 offset){	decoderDecodedBytes = offset;}	void FB_clearWriteToElement(void){	FrameBuffer[g_FB_writeTo].ElementFlag = FT_MIDDLE;}void FB_clearAll(void){	// clears all	uint8 c;	#if (1 == HAVE_WMDRM_LARGE_BUFFER)	for (c = 1; c <= FrameBufferSdramElements; c++)#else		for (c = 1; c <= FrameBufferElements; c++)#endif	{		FrameBuffer[c].status = fbEmpty;		FrameBuffer[c].ElementFlag = FT_MIDDLE;	}		g_FBempty = FrameBufferElements;	// reset FB pointers	g_FB_writeTo = 1;	g_FB_readFrom = 0;}void ClearFBElement(uint8 ElementNumber){	if(FrameBuffer[ElementNumber].status != fbEmpty)	{	  FrameBuffer[ElementNumber].status = fbEmpty;	  g_FBempty++;	}	FrameBuffer[ElementNumber].ElementFlag = FT_MIDDLE;}

⌨️ 快捷键说明

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