📄 buff.c
字号:
//-----------------------------------------------------------------------------
// $Id: buff.c,v 1.0.0 2004/01/13
//-----------------------------------------------------------------------------
//
// ProfiM - PROFIBUS MASTER DRIVER FOR WINDOWS NT/2000
//
// Author:
// Pavel Trnka, CTU FEE
// trnkap@seznam.cz
// With help and advices from:
// Ing. Petr Smolik, CTU FEE
// Ing. Pavel Pisa, CTU FEE
// Ing. Pavel Burget, CTU FEE
//
//-----------------------------------------------------------------------------
//
// Popis:
// ------
// Request Buffer & Result Buffer
//
// Request Buffer (TRequestBuffer) slouzi k ukladani pozadavku do dvou
// oddelenych front Low / High podle jejich priority. Fronta je tvorena
// polem, ktere je cyklicky plneno.
// Result Buffer uklada vysledky pozadavku, ktere byly zpracovany masterem,
// k pozdejsimu vybrani aplikacni vrstvou
//
//-----------------------------------------------------------------------------
//-----------------------------------------------------------------------------
#include "buff.h"
#include "vardef.h"
//*****************************************************************************
//*****************************************************************************
//**
//** Request Buffer
//**
//*****************************************************************************
//*****************************************************************************
void ReqB_Init( PTRequestBuffer ReqB, void *_DeviceExtension )
{
ReqB->LowFirst = 0; // ukazatel na nejstarsi prvek
ReqB->LowLast = 0; // ukazatel na prvni prazdne misto
ReqB->HighFirst = 0;
ReqB->HighLast = 0;
ReqB->DeviceExtension = _DeviceExtension;
}
//*****************************************************************************
void ReqB_Close( PTRequestBuffer ReqB )
{
}
//*****************************************************************************
BOOLEAN ReqB_Empty( PTRequestBuffer ReqB )
{
return ( ReqB_LowEmpty( ReqB ) && ReqB_HighEmpty( ReqB ) );
}
//*****************************************************************************
BOOLEAN ReqB_Full( PTRequestBuffer ReqB, UBYTE priority )
{
if ( priority == low )
return ( ReqB->LowLast + 1 == ReqB->LowFirst ) ||
( ReqB->LowLast == RQ_BUFFER_SIZE - 1 && ReqB->LowFirst == 0 );
if ( priority == high )
return ( ReqB->HighLast + 1 == ReqB->HighFirst ) ||
( ReqB->HighLast == RQ_BUFFER_SIZE - 1 && ReqB->HighFirst == 0 );
return TRUE;
}
//*****************************************************************************
BOOLEAN ReqB_LowEmpty( PTRequestBuffer ReqB )
{
return ( ReqB->LowFirst == ReqB->LowLast );
}
//*****************************************************************************
BOOLEAN ReqB_HighEmpty( PTRequestBuffer ReqB )
{
return ( ReqB->HighFirst == ReqB->HighLast );
}
//*****************************************************************************
int ReqB_LowCount( PTRequestBuffer ReqB )
{
if ( ReqB->LowLast >= ReqB->LowFirst )
{
return ( ReqB->LowLast - ReqB->LowFirst );
}
else
return ( RQ_BUFFER_SIZE - ReqB->LowFirst + ReqB->LowLast );
}
//*****************************************************************************
int ReqB_HighCount( PTRequestBuffer ReqB )
{
if ( ReqB->HighLast >= ReqB->HighFirst )
{
return ( ReqB->HighLast - ReqB->HighFirst );
}
else
return ( RQ_BUFFER_SIZE - ReqB->HighFirst + ReqB->HighLast );
}
//*****************************************************************************
void ReqB_Add( PTRequestBuffer ReqB, fdl_rb *rb )
{
switch ( rb -> rb2_header.priority )
{
case low:
//
// Je-li fronta plna, zahodime nejstarsi pozadavek.
// To neni nejlepsi, ale nemelo by k tomu dochazet.
//
if ( ReqB_Full( ReqB, low ) )
{
ReqB->LowFirst++;
if ( ReqB->LowFirst >= RQ_BUFFER_SIZE )
ReqB->LowFirst = 0;
}
if ( (ReqB->LowLast >= 0) && (ReqB->LowLast < RQ_BUFFER_SIZE) )
ReqB->LowBuffer[ReqB->LowLast++] = *rb;
else
DbgPrint("Profim RQ Buff: Write index ERROR!");
if ( ReqB->LowLast >= RQ_BUFFER_SIZE )
ReqB->LowLast = 0;
break;
//-----------------------------------------------
case high:
//
// Je-li fronta plna, zahodime nejstarsi pozadavek.
//
if ( ReqB_Full( ReqB, high ) )
{
ReqB->HighFirst++;
if ( ReqB->HighFirst >= RQ_BUFFER_SIZE )
ReqB->HighFirst = 0;
}
if ( (ReqB->HighLast >= 0) && (ReqB->HighLast < RQ_BUFFER_SIZE) )
ReqB->HighBuffer[ReqB->HighLast++] = *rb;
else
DbgPrint("Profim RQ Buff: Write index ERROR!");
if ( ReqB->HighLast >= RQ_BUFFER_SIZE )
ReqB->HighLast = 0;
break;
}
}
//*****************************************************************************
// vratit jenom odkaz
void ReqB_GetDeleteNextHigh( PTRequestBuffer ReqB, fdl_rb **rb )
{
if ( ReqB->HighLast != ReqB->HighFirst )
{
if ( (ReqB->HighFirst >= 0) && (ReqB->HighFirst < RQ_BUFFER_SIZE) )
*rb = &( ReqB->HighBuffer[ReqB->HighFirst++] );
else
{
DbgPrint("Profim RQ Buff: Read index ERROR!");
*rb=NULL;
}
if ( ReqB->HighFirst >= RQ_BUFFER_SIZE )
ReqB->HighFirst = 0;
}
else
*rb = NULL;
}
//*****************************************************************************
void ReqB_GetDeleteNextLow( PTRequestBuffer ReqB, fdl_rb **rb )
{
if ( ReqB->LowLast != ReqB->LowFirst )
{
if ( (ReqB->LowFirst >= 0) && (ReqB->LowFirst < RQ_BUFFER_SIZE) )
*rb = &( ReqB->LowBuffer[ReqB->LowFirst++] );
else
{
DbgPrint("Profim RQ Buff: Read index ERROR!");
*rb=NULL;
}
if ( ReqB->LowFirst >= RQ_BUFFER_SIZE )
ReqB->LowFirst = 0;
}
else
*rb=NULL;
}
//*****************************************************************************
//*****************************************************************************
//**
//** Result Buffer
//**
//*****************************************************************************
//*****************************************************************************
void ResB_Init( PTResultBuffer ResB, void *_DeviceExtension )
{
ResB->First = 0; // ukazatel na nejstarsi prvek
ResB->Last = 0; // ukazatel na prvni prazdne misto
ResB->DeviceExtension = _DeviceExtension;
}
//*****************************************************************************
void ResB_Close( PTResultBuffer ResB )
{
}
//*****************************************************************************
BOOLEAN ResB_Empty( PTResultBuffer ResB )
{
return ( ResB->First == ResB->Last );
}
//*****************************************************************************
BOOLEAN ResB_Full( PTResultBuffer ResB )
{
return ( ResB->Last + 1 == ResB->First ) ||
( ResB->Last == RS_BUFFER_SIZE - 1 && ResB->First == 0 );
}
//*****************************************************************************
int ResB_Count( PTResultBuffer ResB )
{
if ( ResB->Last >= ResB->First )
{
return ( ResB->Last - ResB->First );
}
else
return ( RS_BUFFER_SIZE - ResB->First + ResB->Last );
}
//*****************************************************************************
void ResB_Add( PTResultBuffer ResB, fdl_rb *rb )
{
if (!rb || !ResB) {
DbgPrint("Profim ResB_Add: NULL pointer!");
return;
}
//
// Je-li fronta plna, zahodime nejstarsi vysledek.
//
if ( ResB_Full( ResB ) )
{
ResB->First++;
if ( ResB->First >= RS_BUFFER_SIZE )
ResB->First = 0;
}
if ( (ResB->Last >= 0) && (ResB->Last < RS_BUFFER_SIZE) )
//ResB->Buffer[ResB->Last++] = *rb;
RtlMoveMemory( &(ResB->Buffer[ResB->Last++]), rb, sizeof(fdl_rb) );
else
DbgPrint("Profim RS Buff: Write index ERROR!");
if ( ResB->Last >= RS_BUFFER_SIZE )
ResB->Last = 0;
//
// Novy vysledek pridan do bufferu - nasledujici funkce tak
// muze pokracovat ve spracovani pozastaveneho Irp (pending Irp)
//
ResultAdded( ResB->DeviceExtension );
}
//*****************************************************************************
// vrati pouze odkaz
BOOLEAN ResB_GetDeleteNext( PTResultBuffer ResB, fdl_rb **rb )
{
//DbgPrint("Vysledek z pozice %d poslan aplikaci.",ResB->First);
if ( ResB->Last != ResB->First )
{
// *rb = ReqB->Buffer[ ResB->First++ ];
if ( (ResB->First >= 0) && (ResB->First < RS_BUFFER_SIZE) )
*rb = &( ResB->Buffer[ResB->First++] );
else
DbgPrint("Profim RS Buff: Read index ERROR!");
if ( ResB->First >= RS_BUFFER_SIZE )
ResB->First = 0;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -