Staging: epl: fix up some non-ANSI functions
[linux-2.6/linux-acpi-2.6/ibm-acpi-2.6.git] / drivers / staging / epl / EplDllkCal.c
blob0e283d5d018157446ec1d77be296dbf2a1883b19
1 /****************************************************************************
3 (c) SYSTEC electronic GmbH, D-07973 Greiz, August-Bebel-Str. 29
4 www.systec-electronic.com
6 Project: openPOWERLINK
8 Description: source file for kernel DLL Communication Abstraction Layer module
10 License:
12 Redistribution and use in source and binary forms, with or without
13 modification, are permitted provided that the following conditions
14 are met:
16 1. Redistributions of source code must retain the above copyright
17 notice, this list of conditions and the following disclaimer.
19 2. Redistributions in binary form must reproduce the above copyright
20 notice, this list of conditions and the following disclaimer in the
21 documentation and/or other materials provided with the distribution.
23 3. Neither the name of SYSTEC electronic GmbH nor the names of its
24 contributors may be used to endorse or promote products derived
25 from this software without prior written permission. For written
26 permission, please contact info@systec-electronic.com.
28 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
29 "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
30 LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
31 FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
32 COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
33 INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
34 BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
35 LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
36 CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
37 LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
38 ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
39 POSSIBILITY OF SUCH DAMAGE.
41 Severability Clause:
43 If a provision of this License is or becomes illegal, invalid or
44 unenforceable in any jurisdiction, that shall not affect:
45 1. the validity or enforceability in that jurisdiction of any other
46 provision of this License; or
47 2. the validity or enforceability in other jurisdictions of that or
48 any other provision of this License.
50 -------------------------------------------------------------------------
52 $RCSfile: EplDllkCal.c,v $
54 $Author: D.Krueger $
56 $Revision: 1.7 $ $Date: 2008/11/13 17:13:09 $
58 $State: Exp $
60 Build Environment:
61 GCC V3.4
63 -------------------------------------------------------------------------
65 Revision History:
67 2006/06/15 d.k.: start of the implementation, version 1.00
69 ****************************************************************************/
71 #include "kernel/EplDllkCal.h"
72 #include "kernel/EplDllk.h"
73 #include "kernel/EplEventk.h"
75 #include "EplDllCal.h"
76 #ifndef EPL_NO_FIFO
77 #include "SharedBuff.h"
78 #endif
80 #if(((EPL_MODULE_INTEGRATION) & (EPL_MODULE_DLLK)) != 0)
81 /***************************************************************************/
82 /* */
83 /* */
84 /* G L O B A L D E F I N I T I O N S */
85 /* */
86 /* */
87 /***************************************************************************/
89 //---------------------------------------------------------------------------
90 // const defines
91 //---------------------------------------------------------------------------
93 #ifndef min
94 #define min(a,b) (((a) < (b)) ? (a) : (b))
95 #endif
97 //---------------------------------------------------------------------------
98 // local types
99 //---------------------------------------------------------------------------
101 //---------------------------------------------------------------------------
102 // modul globale vars
103 //---------------------------------------------------------------------------
105 //---------------------------------------------------------------------------
106 // local function prototypes
107 //---------------------------------------------------------------------------
109 /***************************************************************************/
110 /* */
111 /* */
112 /* C L A S S EplDllkCal */
113 /* */
114 /* */
115 /***************************************************************************/
117 // Description:
120 /***************************************************************************/
122 //=========================================================================//
123 // //
124 // P R I V A T E D E F I N I T I O N S //
125 // //
126 //=========================================================================//
128 //---------------------------------------------------------------------------
129 // const defines
130 //---------------------------------------------------------------------------
132 #define EPL_DLLKCAL_MAX_QUEUES 5 // CnGenReq, CnNmtReq, {MnGenReq, MnNmtReq}, MnIdentReq, MnStatusReq
134 //---------------------------------------------------------------------------
135 // local types
136 //---------------------------------------------------------------------------
138 typedef struct {
139 #ifndef EPL_NO_FIFO
140 // tShbInstance m_ShbInstanceRx; // FIFO for Rx ASnd frames
141 tShbInstance m_ShbInstanceTxNmt; // FIFO for Tx frames with NMT request priority
142 tShbInstance m_ShbInstanceTxGen; // FIFO for Tx frames with generic priority
143 #else
144 unsigned int m_uiFrameSizeNmt;
145 u8 m_abFrameNmt[1500];
146 unsigned int m_uiFrameSizeGen;
147 u8 m_abFrameGen[1500];
148 #endif
150 tEplDllkCalStatistics m_Statistics;
152 #if (((EPL_MODULE_INTEGRATION) & (EPL_MODULE_NMT_MN)) != 0)
153 // IdentRequest queue with CN node IDs
154 unsigned int m_auiQueueIdentReq[EPL_D_NMT_MaxCNNumber_U8 + 1]; // 1 entry is reserved to distinguish between full and empty
155 unsigned int m_uiWriteIdentReq;
156 unsigned int m_uiReadIdentReq;
158 // StatusRequest queue with CN node IDs
159 unsigned int m_auiQueueStatusReq[EPL_D_NMT_MaxCNNumber_U8 + 1]; // 1 entry is reserved to distinguish between full and empty
160 unsigned int m_uiWriteStatusReq;
161 unsigned int m_uiReadStatusReq;
163 unsigned int m_auiQueueCnRequests[254 * 2];
164 // first 254 entries represent the generic requests of the corresponding node
165 // second 254 entries represent the NMT requests of the corresponding node
166 unsigned int m_uiNextQueueCnRequest;
167 unsigned int m_uiNextRequestQueue;
168 #endif
170 } tEplDllkCalInstance;
172 //---------------------------------------------------------------------------
173 // local vars
174 //---------------------------------------------------------------------------
176 // if no dynamic memory allocation shall be used
177 // define structures statically
178 static tEplDllkCalInstance EplDllkCalInstance_g;
180 //---------------------------------------------------------------------------
181 // local function prototypes
182 //---------------------------------------------------------------------------
184 //=========================================================================//
185 // //
186 // P U B L I C F U N C T I O N S //
187 // //
188 //=========================================================================//
190 //---------------------------------------------------------------------------
192 // Function: EplDllkCalAddInstance()
194 // Description: add and initialize new instance of DLL CAL module
196 // Parameters: none
198 // Returns: tEplKernel = error code
201 // State:
203 //---------------------------------------------------------------------------
205 tEplKernel EplDllkCalAddInstance(void)
207 tEplKernel Ret = kEplSuccessful;
208 #ifndef EPL_NO_FIFO
209 tShbError ShbError;
210 unsigned int fShbNewCreated;
212 /* ShbError = ShbCirAllocBuffer (EPL_DLLCAL_BUFFER_SIZE_RX, EPL_DLLCAL_BUFFER_ID_RX,
213 &EplDllkCalInstance_g.m_ShbInstanceRx, &fShbNewCreated);
214 // returns kShbOk, kShbOpenMismatch, kShbOutOfMem or kShbInvalidArg
216 if (ShbError != kShbOk)
218 Ret = kEplNoResource;
221 ShbError =
222 ShbCirAllocBuffer(EPL_DLLCAL_BUFFER_SIZE_TX_NMT,
223 EPL_DLLCAL_BUFFER_ID_TX_NMT,
224 &EplDllkCalInstance_g.m_ShbInstanceTxNmt,
225 &fShbNewCreated);
226 // returns kShbOk, kShbOpenMismatch, kShbOutOfMem or kShbInvalidArg
228 if (ShbError != kShbOk) {
229 Ret = kEplNoResource;
232 /* ShbError = ShbCirSetSignalHandlerNewData (EplDllkCalInstance_g.m_ShbInstanceTxNmt, EplDllkCalTxNmtSignalHandler, kShbPriorityNormal);
233 // returns kShbOk, kShbAlreadySignaling or kShbInvalidArg
235 if (ShbError != kShbOk)
237 Ret = kEplNoResource;
240 ShbError =
241 ShbCirAllocBuffer(EPL_DLLCAL_BUFFER_SIZE_TX_GEN,
242 EPL_DLLCAL_BUFFER_ID_TX_GEN,
243 &EplDllkCalInstance_g.m_ShbInstanceTxGen,
244 &fShbNewCreated);
245 // returns kShbOk, kShbOpenMismatch, kShbOutOfMem or kShbInvalidArg
247 if (ShbError != kShbOk) {
248 Ret = kEplNoResource;
251 /* ShbError = ShbCirSetSignalHandlerNewData (EplDllkCalInstance_g.m_ShbInstanceTxGen, EplDllkCalTxGenSignalHandler, kShbPriorityNormal);
252 // returns kShbOk, kShbAlreadySignaling or kShbInvalidArg
254 if (ShbError != kShbOk)
256 Ret = kEplNoResource;
259 #else
260 EplDllkCalInstance_g.m_uiFrameSizeNmt = 0;
261 EplDllkCalInstance_g.m_uiFrameSizeGen = 0;
262 #endif
264 return Ret;
267 //---------------------------------------------------------------------------
269 // Function: EplDllkCalDelInstance()
271 // Description: deletes instance of DLL CAL module
273 // Parameters: none
275 // Returns: tEplKernel = error code
278 // State:
280 //---------------------------------------------------------------------------
282 tEplKernel EplDllkCalDelInstance(void)
284 tEplKernel Ret = kEplSuccessful;
285 #ifndef EPL_NO_FIFO
286 tShbError ShbError;
288 /* ShbError = ShbCirReleaseBuffer (EplDllkCalInstance_g.m_ShbInstanceRx);
289 if (ShbError != kShbOk)
291 Ret = kEplNoResource;
293 EplDllkCalInstance_g.m_ShbInstanceRx = NULL;
295 ShbError = ShbCirReleaseBuffer(EplDllkCalInstance_g.m_ShbInstanceTxNmt);
296 if (ShbError != kShbOk) {
297 Ret = kEplNoResource;
299 EplDllkCalInstance_g.m_ShbInstanceTxNmt = NULL;
301 ShbError = ShbCirReleaseBuffer(EplDllkCalInstance_g.m_ShbInstanceTxGen);
302 if (ShbError != kShbOk) {
303 Ret = kEplNoResource;
305 EplDllkCalInstance_g.m_ShbInstanceTxGen = NULL;
307 #else
308 EplDllkCalInstance_g.m_uiFrameSizeNmt = 0;
309 EplDllkCalInstance_g.m_uiFrameSizeGen = 0;
310 #endif
312 return Ret;
315 //---------------------------------------------------------------------------
317 // Function: EplDllkCalProcess
319 // Description: process the passed configuration
321 // Parameters: pEvent_p = event containing configuration options
323 // Returns: tEplKernel = error code
326 // State:
328 //---------------------------------------------------------------------------
330 tEplKernel EplDllkCalProcess(tEplEvent * pEvent_p)
332 tEplKernel Ret = kEplSuccessful;
334 switch (pEvent_p->m_EventType) {
335 case kEplEventTypeDllkServFilter:
337 tEplDllCalAsndServiceIdFilter *pServFilter;
339 pServFilter =
340 (tEplDllCalAsndServiceIdFilter *) pEvent_p->m_pArg;
341 Ret =
342 EplDllkSetAsndServiceIdFilter(pServFilter->
343 m_ServiceId,
344 pServFilter->
345 m_Filter);
346 break;
349 #if (((EPL_MODULE_INTEGRATION) & (EPL_MODULE_NMT_MN)) != 0)
350 case kEplEventTypeDllkIssueReq:
352 tEplDllCalIssueRequest *pIssueReq;
354 pIssueReq = (tEplDllCalIssueRequest *) pEvent_p->m_pArg;
355 Ret =
356 EplDllkCalIssueRequest(pIssueReq->m_Service,
357 pIssueReq->m_uiNodeId,
358 pIssueReq->m_bSoaFlag1);
359 break;
362 case kEplEventTypeDllkAddNode:
364 tEplDllNodeInfo *pNodeInfo;
366 pNodeInfo = (tEplDllNodeInfo *) pEvent_p->m_pArg;
367 Ret = EplDllkAddNode(pNodeInfo);
368 break;
371 case kEplEventTypeDllkDelNode:
373 unsigned int *puiNodeId;
375 puiNodeId = (unsigned int *)pEvent_p->m_pArg;
376 Ret = EplDllkDeleteNode(*puiNodeId);
377 break;
380 case kEplEventTypeDllkSoftDelNode:
382 unsigned int *puiNodeId;
384 puiNodeId = (unsigned int *)pEvent_p->m_pArg;
385 Ret = EplDllkSoftDeleteNode(*puiNodeId);
386 break;
388 #endif
390 case kEplEventTypeDllkIdentity:
392 tEplDllIdentParam *pIdentParam;
394 pIdentParam = (tEplDllIdentParam *) pEvent_p->m_pArg;
395 if (pIdentParam->m_uiSizeOfStruct > pEvent_p->m_uiSize) {
396 pIdentParam->m_uiSizeOfStruct =
397 pEvent_p->m_uiSize;
399 Ret = EplDllkSetIdentity(pIdentParam);
400 break;
403 case kEplEventTypeDllkConfig:
405 tEplDllConfigParam *pConfigParam;
407 pConfigParam = (tEplDllConfigParam *) pEvent_p->m_pArg;
408 if (pConfigParam->m_uiSizeOfStruct > pEvent_p->m_uiSize) {
409 pConfigParam->m_uiSizeOfStruct =
410 pEvent_p->m_uiSize;
412 Ret = EplDllkConfig(pConfigParam);
413 break;
416 default:
417 break;
420 //Exit:
421 return Ret;
424 //---------------------------------------------------------------------------
426 // Function: EplDllkCalAsyncGetTxCount()
428 // Description: returns count of Tx frames of FIFO with highest priority
430 // Parameters: none
432 // Returns: tEplKernel = error code
435 // State:
437 //---------------------------------------------------------------------------
439 tEplKernel EplDllkCalAsyncGetTxCount(tEplDllAsyncReqPriority * pPriority_p,
440 unsigned int *puiCount_p)
442 tEplKernel Ret = kEplSuccessful;
443 #ifndef EPL_NO_FIFO
444 tShbError ShbError;
445 unsigned long ulFrameCount;
447 // get frame count of Tx FIFO with NMT request priority
448 ShbError =
449 ShbCirGetReadBlockCount(EplDllkCalInstance_g.m_ShbInstanceTxNmt,
450 &ulFrameCount);
451 // returns kShbOk, kShbInvalidArg
453 // error handling
454 if (ShbError != kShbOk) {
455 Ret = kEplNoResource;
456 goto Exit;
459 if (ulFrameCount >
460 EplDllkCalInstance_g.m_Statistics.m_ulMaxTxFrameCountNmt) {
461 EplDllkCalInstance_g.m_Statistics.m_ulMaxTxFrameCountNmt =
462 ulFrameCount;
465 if (ulFrameCount != 0) { // NMT requests are in queue
466 *pPriority_p = kEplDllAsyncReqPrioNmt;
467 *puiCount_p = (unsigned int)ulFrameCount;
468 goto Exit;
470 // get frame count of Tx FIFO with generic priority
471 ShbError =
472 ShbCirGetReadBlockCount(EplDllkCalInstance_g.m_ShbInstanceTxGen,
473 &ulFrameCount);
474 // returns kShbOk, kShbInvalidArg
476 // error handling
477 if (ShbError != kShbOk) {
478 Ret = kEplNoResource;
479 goto Exit;
482 if (ulFrameCount >
483 EplDllkCalInstance_g.m_Statistics.m_ulMaxTxFrameCountGen) {
484 EplDllkCalInstance_g.m_Statistics.m_ulMaxTxFrameCountGen =
485 ulFrameCount;
488 *pPriority_p = kEplDllAsyncReqPrioGeneric;
489 *puiCount_p = (unsigned int)ulFrameCount;
491 Exit:
492 #else
493 if (EplDllkCalInstance_g.m_uiFrameSizeNmt > 0) {
494 *pPriority_p = kEplDllAsyncReqPrioNmt;
495 *puiCount_p = 1;
496 } else if (EplDllkCalInstance_g.m_uiFrameSizeGen > 0) {
497 *pPriority_p = kEplDllAsyncReqPrioGeneric;
498 *puiCount_p = 1;
499 } else {
500 *pPriority_p = kEplDllAsyncReqPrioGeneric;
501 *puiCount_p = 0;
503 #endif
505 return Ret;
508 //---------------------------------------------------------------------------
510 // Function: EplDllkCalAsyncGetTxFrame()
512 // Description: returns Tx frames from FIFO with specified priority
514 // Parameters: pFrame_p = IN: pointer to buffer
515 // puiFrameSize_p = IN: max size of buffer
516 // OUT: actual size of frame
517 // Priority_p = IN: priority
519 // Returns: tEplKernel = error code
522 // State:
524 //---------------------------------------------------------------------------
526 tEplKernel EplDllkCalAsyncGetTxFrame(void *pFrame_p,
527 unsigned int *puiFrameSize_p,
528 tEplDllAsyncReqPriority Priority_p)
530 tEplKernel Ret = kEplSuccessful;
531 #ifndef EPL_NO_FIFO
532 tShbError ShbError;
533 unsigned long ulFrameSize;
535 switch (Priority_p) {
536 case kEplDllAsyncReqPrioNmt: // NMT request priority
537 ShbError =
538 ShbCirReadDataBlock(EplDllkCalInstance_g.m_ShbInstanceTxNmt,
539 (u8 *) pFrame_p, *puiFrameSize_p,
540 &ulFrameSize);
541 // returns kShbOk, kShbDataTruncated, kShbInvalidArg, kShbNoReadableData
542 break;
544 default: // generic priority
545 ShbError =
546 ShbCirReadDataBlock(EplDllkCalInstance_g.m_ShbInstanceTxGen,
547 (u8 *) pFrame_p, *puiFrameSize_p,
548 &ulFrameSize);
549 // returns kShbOk, kShbDataTruncated, kShbInvalidArg, kShbNoReadableData
550 break;
554 // error handling
555 if (ShbError != kShbOk) {
556 if (ShbError == kShbNoReadableData) {
557 Ret = kEplDllAsyncTxBufferEmpty;
558 } else { // other error
559 Ret = kEplNoResource;
561 goto Exit;
564 *puiFrameSize_p = (unsigned int)ulFrameSize;
566 Exit:
567 #else
568 switch (Priority_p) {
569 case kEplDllAsyncReqPrioNmt: // NMT request priority
570 *puiFrameSize_p =
571 min(*puiFrameSize_p, EplDllkCalInstance_g.m_uiFrameSizeNmt);
572 EPL_MEMCPY(pFrame_p, EplDllkCalInstance_g.m_abFrameNmt,
573 *puiFrameSize_p);
574 EplDllkCalInstance_g.m_uiFrameSizeNmt = 0;
575 break;
577 default: // generic priority
578 *puiFrameSize_p =
579 min(*puiFrameSize_p, EplDllkCalInstance_g.m_uiFrameSizeGen);
580 EPL_MEMCPY(pFrame_p, EplDllkCalInstance_g.m_abFrameGen,
581 *puiFrameSize_p);
582 EplDllkCalInstance_g.m_uiFrameSizeGen = 0;
583 break;
586 #endif
588 return Ret;
591 //---------------------------------------------------------------------------
593 // Function: EplDllkCalAsyncFrameReceived()
595 // Description: passes ASnd frame to receive FIFO.
596 // It will be called only for frames with registered AsndServiceIds.
598 // Parameters: none
600 // Returns: tEplKernel = error code
603 // State:
605 //---------------------------------------------------------------------------
607 tEplKernel EplDllkCalAsyncFrameReceived(tEplFrameInfo * pFrameInfo_p)
609 tEplKernel Ret = kEplSuccessful;
610 tEplEvent Event;
612 Event.m_EventSink = kEplEventSinkDlluCal;
613 Event.m_EventType = kEplEventTypeAsndRx;
614 Event.m_pArg = pFrameInfo_p->m_pFrame;
615 Event.m_uiSize = pFrameInfo_p->m_uiFrameSize;
616 // pass NetTime of frame to userspace
617 Event.m_NetTime = pFrameInfo_p->m_NetTime;
619 Ret = EplEventkPost(&Event);
620 if (Ret != kEplSuccessful) {
621 EplDllkCalInstance_g.m_Statistics.m_ulCurRxFrameCount++;
622 } else {
623 EplDllkCalInstance_g.m_Statistics.m_ulMaxRxFrameCount++;
626 return Ret;
629 //---------------------------------------------------------------------------
631 // Function: EplDllkCalAsyncSend()
633 // Description: puts the given frame into the transmit FIFO with the specified
634 // priority.
636 // Parameters: pFrameInfo_p = frame info structure
637 // Priority_p = priority
639 // Returns: tEplKernel = error code
642 // State:
644 //---------------------------------------------------------------------------
646 tEplKernel EplDllkCalAsyncSend(tEplFrameInfo * pFrameInfo_p,
647 tEplDllAsyncReqPriority Priority_p)
649 tEplKernel Ret = kEplSuccessful;
650 tEplEvent Event;
651 #ifndef EPL_NO_FIFO
652 tShbError ShbError;
654 switch (Priority_p) {
655 case kEplDllAsyncReqPrioNmt: // NMT request priority
656 ShbError =
657 ShbCirWriteDataBlock(EplDllkCalInstance_g.
658 m_ShbInstanceTxNmt,
659 pFrameInfo_p->m_pFrame,
660 pFrameInfo_p->m_uiFrameSize);
661 // returns kShbOk, kShbExceedDataSizeLimit, kShbBufferFull, kShbInvalidArg
662 break;
664 default: // generic priority
665 ShbError =
666 ShbCirWriteDataBlock(EplDllkCalInstance_g.
667 m_ShbInstanceTxGen,
668 pFrameInfo_p->m_pFrame,
669 pFrameInfo_p->m_uiFrameSize);
670 // returns kShbOk, kShbExceedDataSizeLimit, kShbBufferFull, kShbInvalidArg
671 break;
675 // error handling
676 switch (ShbError) {
677 case kShbOk:
678 break;
680 case kShbExceedDataSizeLimit:
681 Ret = kEplDllAsyncTxBufferFull;
682 break;
684 case kShbBufferFull:
685 Ret = kEplDllAsyncTxBufferFull;
686 break;
688 case kShbInvalidArg:
689 default:
690 Ret = kEplNoResource;
691 break;
694 #else
696 switch (Priority_p) {
697 case kEplDllAsyncReqPrioNmt: // NMT request priority
698 if (EplDllkCalInstance_g.m_uiFrameSizeNmt == 0) {
699 EPL_MEMCPY(EplDllkCalInstance_g.m_abFrameNmt,
700 pFrameInfo_p->m_pFrame,
701 pFrameInfo_p->m_uiFrameSize);
702 EplDllkCalInstance_g.m_uiFrameSizeNmt =
703 pFrameInfo_p->m_uiFrameSize;
704 } else {
705 Ret = kEplDllAsyncTxBufferFull;
706 goto Exit;
708 break;
710 default: // generic priority
711 if (EplDllkCalInstance_g.m_uiFrameSizeGen == 0) {
712 EPL_MEMCPY(EplDllkCalInstance_g.m_abFrameGen,
713 pFrameInfo_p->m_pFrame,
714 pFrameInfo_p->m_uiFrameSize);
715 EplDllkCalInstance_g.m_uiFrameSizeGen =
716 pFrameInfo_p->m_uiFrameSize;
717 } else {
718 Ret = kEplDllAsyncTxBufferFull;
719 goto Exit;
721 break;
724 #endif
726 // post event to DLL
727 Event.m_EventSink = kEplEventSinkDllk;
728 Event.m_EventType = kEplEventTypeDllkFillTx;
729 EPL_MEMSET(&Event.m_NetTime, 0x00, sizeof(Event.m_NetTime));
730 Event.m_pArg = &Priority_p;
731 Event.m_uiSize = sizeof(Priority_p);
732 Ret = EplEventkPost(&Event);
734 #ifdef EPL_NO_FIFO
735 Exit:
736 #endif
738 return Ret;
741 //---------------------------------------------------------------------------
743 // Function: EplDllkCalAsyncClearBuffer()
745 // Description: clears the transmit buffer
747 // Parameters: (none)
749 // Returns: tEplKernel = error code
752 // State:
754 //---------------------------------------------------------------------------
756 tEplKernel EplDllkCalAsyncClearBuffer(void)
758 tEplKernel Ret = kEplSuccessful;
759 #ifndef EPL_NO_FIFO
760 tShbError ShbError;
762 ShbError =
763 ShbCirResetBuffer(EplDllkCalInstance_g.m_ShbInstanceTxNmt, 1000,
764 NULL);
765 ShbError =
766 ShbCirResetBuffer(EplDllkCalInstance_g.m_ShbInstanceTxGen, 1000,
767 NULL);
769 #else
770 EplDllkCalInstance_g.m_uiFrameSizeNmt = 0;
771 EplDllkCalInstance_g.m_uiFrameSizeGen = 0;
772 #endif
774 // EPL_MEMSET(&EplDllkCalInstance_g.m_Statistics, 0, sizeof (tEplDllkCalStatistics));
775 return Ret;
778 //---------------------------------------------------------------------------
780 // Function: EplDllkCalAsyncClearQueues()
782 // Description: clears the transmit buffer
784 // Parameters: (none)
786 // Returns: tEplKernel = error code
789 // State:
791 //---------------------------------------------------------------------------
793 #if (((EPL_MODULE_INTEGRATION) & (EPL_MODULE_NMT_MN)) != 0)
794 tEplKernel EplDllkCalAsyncClearQueues(void)
796 tEplKernel Ret = kEplSuccessful;
798 // clear MN asynchronous queues
799 EplDllkCalInstance_g.m_uiNextQueueCnRequest = 0;
800 EplDllkCalInstance_g.m_uiNextRequestQueue = 0;
801 EplDllkCalInstance_g.m_uiReadIdentReq = 0;
802 EplDllkCalInstance_g.m_uiWriteIdentReq = 0;
803 EplDllkCalInstance_g.m_uiReadStatusReq = 0;
804 EplDllkCalInstance_g.m_uiWriteStatusReq = 0;
806 return Ret;
808 #endif
810 //---------------------------------------------------------------------------
812 // Function: EplDllkCalGetStatistics()
814 // Description: returns statistics of the asynchronous queues.
816 // Parameters: ppStatistics = statistics structure
818 // Returns: tEplKernel = error code
821 // State:
823 //---------------------------------------------------------------------------
825 tEplKernel EplDllkCalGetStatistics(tEplDllkCalStatistics ** ppStatistics)
827 tEplKernel Ret = kEplSuccessful;
828 #ifndef EPL_NO_FIFO
829 tShbError ShbError;
831 ShbError =
832 ShbCirGetReadBlockCount(EplDllkCalInstance_g.m_ShbInstanceTxNmt,
833 &EplDllkCalInstance_g.m_Statistics.
834 m_ulCurTxFrameCountNmt);
835 ShbError =
836 ShbCirGetReadBlockCount(EplDllkCalInstance_g.m_ShbInstanceTxGen,
837 &EplDllkCalInstance_g.m_Statistics.
838 m_ulCurTxFrameCountGen);
839 // ShbError = ShbCirGetReadBlockCount (EplDllkCalInstance_g.m_ShbInstanceRx, &EplDllkCalInstance_g.m_Statistics.m_ulCurRxFrameCount);
841 #else
842 if (EplDllkCalInstance_g.m_uiFrameSizeNmt > 0) {
843 EplDllkCalInstance_g.m_Statistics.m_ulCurTxFrameCountNmt = 1;
844 } else {
845 EplDllkCalInstance_g.m_Statistics.m_ulCurTxFrameCountNmt = 0;
847 if (EplDllkCalInstance_g.m_uiFrameSizeGen > 0) {
848 EplDllkCalInstance_g.m_Statistics.m_ulCurTxFrameCountGen = 1;
849 } else {
850 EplDllkCalInstance_g.m_Statistics.m_ulCurTxFrameCountGen = 0;
852 #endif
854 *ppStatistics = &EplDllkCalInstance_g.m_Statistics;
855 return Ret;
858 #if (((EPL_MODULE_INTEGRATION) & (EPL_MODULE_NMT_MN)) != 0)
860 //---------------------------------------------------------------------------
862 // Function: EplDllkCalIssueRequest()
864 // Description: issues a StatusRequest or a IdentRequest to the specified node.
866 // Parameters: Service_p = request service ID
867 // uiNodeId_p = node ID
868 // bSoaFlag1_p = flag1 for this node (transmit in SoA and PReq)
869 // If 0xFF this flag is ignored.
871 // Returns: tEplKernel = error code
874 // State:
876 //---------------------------------------------------------------------------
878 tEplKernel EplDllkCalIssueRequest(tEplDllReqServiceId Service_p,
879 unsigned int uiNodeId_p, u8 bSoaFlag1_p)
881 tEplKernel Ret = kEplSuccessful;
883 if (bSoaFlag1_p != 0xFF) {
884 Ret = EplDllkSetFlag1OfNode(uiNodeId_p, bSoaFlag1_p);
885 if (Ret != kEplSuccessful) {
886 goto Exit;
889 // add node to appropriate request queue
890 switch (Service_p) {
891 case kEplDllReqServiceIdent:
893 if (((EplDllkCalInstance_g.m_uiWriteIdentReq +
894 1) %
895 tabentries(EplDllkCalInstance_g.
896 m_auiQueueIdentReq))
897 == EplDllkCalInstance_g.m_uiReadIdentReq) { // queue is full
898 Ret = kEplDllAsyncTxBufferFull;
899 goto Exit;
901 EplDllkCalInstance_g.
902 m_auiQueueIdentReq[EplDllkCalInstance_g.
903 m_uiWriteIdentReq] = uiNodeId_p;
904 EplDllkCalInstance_g.m_uiWriteIdentReq =
905 (EplDllkCalInstance_g.m_uiWriteIdentReq +
906 1) %
907 tabentries(EplDllkCalInstance_g.m_auiQueueIdentReq);
908 break;
911 case kEplDllReqServiceStatus:
913 if (((EplDllkCalInstance_g.m_uiWriteStatusReq +
914 1) %
915 tabentries(EplDllkCalInstance_g.
916 m_auiQueueStatusReq))
917 == EplDllkCalInstance_g.m_uiReadStatusReq) { // queue is full
918 Ret = kEplDllAsyncTxBufferFull;
919 goto Exit;
921 EplDllkCalInstance_g.
922 m_auiQueueStatusReq[EplDllkCalInstance_g.
923 m_uiWriteStatusReq] =
924 uiNodeId_p;
925 EplDllkCalInstance_g.m_uiWriteStatusReq =
926 (EplDllkCalInstance_g.m_uiWriteStatusReq +
927 1) %
928 tabentries(EplDllkCalInstance_g.
929 m_auiQueueStatusReq);
930 break;
933 default:
935 Ret = kEplDllInvalidParam;
936 goto Exit;
940 Exit:
941 return Ret;
944 //---------------------------------------------------------------------------
946 // Function: EplDllkCalAsyncGetSoaRequest()
948 // Description: returns next request for SoA. This function is called by DLLk module.
950 // Parameters: pReqServiceId_p = pointer to request service ID
951 // IN: available request for MN NMT or generic request queue (Flag2.PR)
952 // or kEplDllReqServiceNo if queues are empty
953 // OUT: next request
954 // puiNodeId_p = OUT: pointer to node ID of next request
955 // = EPL_C_ADR_INVALID, if request is self addressed
957 // Returns: tEplKernel = error code
960 // State:
962 //---------------------------------------------------------------------------
964 tEplKernel EplDllkCalAsyncGetSoaRequest(tEplDllReqServiceId * pReqServiceId_p,
965 unsigned int *puiNodeId_p)
967 tEplKernel Ret = kEplSuccessful;
968 unsigned int uiCount;
970 // *pReqServiceId_p = kEplDllReqServiceNo;
972 for (uiCount = EPL_DLLKCAL_MAX_QUEUES; uiCount > 0; uiCount--) {
973 switch (EplDllkCalInstance_g.m_uiNextRequestQueue) {
974 case 0:
975 { // CnGenReq
976 for (;
977 EplDllkCalInstance_g.
978 m_uiNextQueueCnRequest <
979 (tabentries
980 (EplDllkCalInstance_g.
981 m_auiQueueCnRequests) / 2);
982 EplDllkCalInstance_g.
983 m_uiNextQueueCnRequest++) {
984 if (EplDllkCalInstance_g.m_auiQueueCnRequests[EplDllkCalInstance_g.m_uiNextQueueCnRequest] > 0) { // non empty queue found
985 // remove one request from queue
986 EplDllkCalInstance_g.
987 m_auiQueueCnRequests
988 [EplDllkCalInstance_g.
989 m_uiNextQueueCnRequest]--;
990 *puiNodeId_p =
991 EplDllkCalInstance_g.
992 m_uiNextQueueCnRequest + 1;
993 *pReqServiceId_p =
994 kEplDllReqServiceUnspecified;
995 EplDllkCalInstance_g.
996 m_uiNextQueueCnRequest++;
997 if (EplDllkCalInstance_g.m_uiNextQueueCnRequest >= (tabentries(EplDllkCalInstance_g.m_auiQueueCnRequests) / 2)) { // last node reached
998 // continue with CnNmtReq queue at next SoA
999 EplDllkCalInstance_g.
1000 m_uiNextRequestQueue
1001 = 1;
1003 goto Exit;
1006 // all CnGenReq queues are empty -> continue with CnNmtReq queue
1007 EplDllkCalInstance_g.m_uiNextRequestQueue = 1;
1008 break;
1011 case 1:
1012 { // CnNmtReq
1013 for (;
1014 EplDllkCalInstance_g.
1015 m_uiNextQueueCnRequest <
1016 tabentries(EplDllkCalInstance_g.
1017 m_auiQueueCnRequests);
1018 EplDllkCalInstance_g.
1019 m_uiNextQueueCnRequest++) {
1020 if (EplDllkCalInstance_g.m_auiQueueCnRequests[EplDllkCalInstance_g.m_uiNextQueueCnRequest] > 0) { // non empty queue found
1021 // remove one request from queue
1022 EplDllkCalInstance_g.
1023 m_auiQueueCnRequests
1024 [EplDllkCalInstance_g.
1025 m_uiNextQueueCnRequest]--;
1026 *puiNodeId_p =
1027 EplDllkCalInstance_g.
1028 m_uiNextQueueCnRequest + 1 -
1029 (tabentries
1030 (EplDllkCalInstance_g.
1031 m_auiQueueCnRequests) /
1033 *pReqServiceId_p =
1034 kEplDllReqServiceNmtRequest;
1035 EplDllkCalInstance_g.
1036 m_uiNextQueueCnRequest++;
1037 if (EplDllkCalInstance_g.m_uiNextQueueCnRequest > tabentries(EplDllkCalInstance_g.m_auiQueueCnRequests)) { // last node reached
1038 // restart CnGenReq queue
1039 EplDllkCalInstance_g.
1040 m_uiNextQueueCnRequest
1041 = 0;
1042 // continue with MnGenReq queue at next SoA
1043 EplDllkCalInstance_g.
1044 m_uiNextRequestQueue
1045 = 2;
1047 goto Exit;
1050 // restart CnGenReq queue
1051 EplDllkCalInstance_g.m_uiNextQueueCnRequest = 0;
1052 // all CnNmtReq queues are empty -> continue with MnGenReq queue
1053 EplDllkCalInstance_g.m_uiNextRequestQueue = 2;
1054 break;
1057 case 2:
1058 { // MnNmtReq and MnGenReq
1059 // next queue will be MnIdentReq queue
1060 EplDllkCalInstance_g.m_uiNextRequestQueue = 3;
1061 if (*pReqServiceId_p != kEplDllReqServiceNo) {
1062 *puiNodeId_p = EPL_C_ADR_INVALID; // DLLk must exchange this with the actual node ID
1063 goto Exit;
1065 break;
1068 case 3:
1069 { // MnIdentReq
1070 // next queue will be MnStatusReq queue
1071 EplDllkCalInstance_g.m_uiNextRequestQueue = 4;
1072 if (EplDllkCalInstance_g.m_uiReadIdentReq != EplDllkCalInstance_g.m_uiWriteIdentReq) { // queue is not empty
1073 *puiNodeId_p =
1074 EplDllkCalInstance_g.
1075 m_auiQueueIdentReq
1076 [EplDllkCalInstance_g.
1077 m_uiReadIdentReq];
1078 EplDllkCalInstance_g.m_uiReadIdentReq =
1079 (EplDllkCalInstance_g.
1080 m_uiReadIdentReq +
1081 1) %
1082 tabentries(EplDllkCalInstance_g.
1083 m_auiQueueIdentReq);
1084 *pReqServiceId_p =
1085 kEplDllReqServiceIdent;
1086 goto Exit;
1088 break;
1091 case 4:
1092 { // MnStatusReq
1093 // next queue will be CnGenReq queue
1094 EplDllkCalInstance_g.m_uiNextRequestQueue = 0;
1095 if (EplDllkCalInstance_g.m_uiReadStatusReq != EplDllkCalInstance_g.m_uiWriteStatusReq) { // queue is not empty
1096 *puiNodeId_p =
1097 EplDllkCalInstance_g.
1098 m_auiQueueStatusReq
1099 [EplDllkCalInstance_g.
1100 m_uiReadStatusReq];
1101 EplDllkCalInstance_g.m_uiReadStatusReq =
1102 (EplDllkCalInstance_g.
1103 m_uiReadStatusReq +
1104 1) %
1105 tabentries(EplDllkCalInstance_g.
1106 m_auiQueueStatusReq);
1107 *pReqServiceId_p =
1108 kEplDllReqServiceStatus;
1109 goto Exit;
1111 break;
1117 Exit:
1118 return Ret;
1121 //---------------------------------------------------------------------------
1123 // Function: EplDllkCalAsyncSetPendingRequests()
1125 // Description: sets the pending asynchronous frame requests of the specified node.
1126 // This will add the node to the asynchronous request scheduler.
1128 // Parameters: uiNodeId_p = node ID
1129 // AsyncReqPrio_p = asynchronous request priority
1130 // uiCount_p = count of asynchronous frames
1132 // Returns: tEplKernel = error code
1135 // State:
1137 //---------------------------------------------------------------------------
1139 tEplKernel EplDllkCalAsyncSetPendingRequests(unsigned int uiNodeId_p,
1140 tEplDllAsyncReqPriority
1141 AsyncReqPrio_p,
1142 unsigned int uiCount_p)
1144 tEplKernel Ret = kEplSuccessful;
1146 // add node to appropriate request queue
1147 switch (AsyncReqPrio_p) {
1148 case kEplDllAsyncReqPrioNmt:
1150 uiNodeId_p--;
1151 if (uiNodeId_p >=
1152 (tabentries
1153 (EplDllkCalInstance_g.m_auiQueueCnRequests) / 2)) {
1154 Ret = kEplDllInvalidParam;
1155 goto Exit;
1157 uiNodeId_p +=
1158 tabentries(EplDllkCalInstance_g.
1159 m_auiQueueCnRequests) / 2;
1160 EplDllkCalInstance_g.m_auiQueueCnRequests[uiNodeId_p] =
1161 uiCount_p;
1162 break;
1165 default:
1167 uiNodeId_p--;
1168 if (uiNodeId_p >=
1169 (tabentries
1170 (EplDllkCalInstance_g.m_auiQueueCnRequests) / 2)) {
1171 Ret = kEplDllInvalidParam;
1172 goto Exit;
1174 EplDllkCalInstance_g.m_auiQueueCnRequests[uiNodeId_p] =
1175 uiCount_p;
1176 break;
1180 Exit:
1181 return Ret;
1183 #endif //(((EPL_MODULE_INTEGRATION) & (EPL_MODULE_NMT_MN)) != 0)
1185 //=========================================================================//
1186 // //
1187 // P R I V A T E F U N C T I O N S //
1188 // //
1189 //=========================================================================//
1191 //---------------------------------------------------------------------------
1192 // Callback handler for new data signaling
1193 //---------------------------------------------------------------------------
1195 #ifndef EPL_NO_FIFO
1196 /*static void EplDllkCalTxNmtSignalHandler (
1197 tShbInstance pShbRxInstance_p,
1198 unsigned long ulDataSize_p)
1200 tEplKernel Ret = kEplSuccessful;
1201 tEplEvent Event;
1202 tEplDllAsyncReqPriority Priority;
1203 #ifndef EPL_NO_FIFO
1204 tShbError ShbError;
1205 unsigned long ulBlockCount;
1207 ShbError = ShbCirGetReadBlockCount (EplDllkCalInstance_g.m_ShbInstanceTxNmt, &ulBlockCount);
1208 if (ulBlockCount > EplDllkCalInstance_g.m_Statistics.m_ulMaxTxFrameCountNmt)
1210 EplDllkCalInstance_g.m_Statistics.m_ulMaxTxFrameCountNmt = ulBlockCount;
1213 #endif
1215 // post event to DLL
1216 Priority = kEplDllAsyncReqPrioNmt;
1217 Event.m_EventSink = kEplEventSinkDllk;
1218 Event.m_EventType = kEplEventTypeDllkFillTx;
1219 EPL_MEMSET(&Event.m_NetTime, 0x00, sizeof(Event.m_NetTime));
1220 Event.m_pArg = &Priority;
1221 Event.m_uiSize = sizeof(Priority);
1222 Ret = EplEventkPost(&Event);
1226 static void EplDllkCalTxGenSignalHandler (
1227 tShbInstance pShbRxInstance_p,
1228 unsigned long ulDataSize_p)
1230 tEplKernel Ret = kEplSuccessful;
1231 tEplEvent Event;
1232 tEplDllAsyncReqPriority Priority;
1233 #ifndef EPL_NO_FIFO
1234 tShbError ShbError;
1235 unsigned long ulBlockCount;
1237 ShbError = ShbCirGetReadBlockCount (EplDllkCalInstance_g.m_ShbInstanceTxGen, &ulBlockCount);
1238 if (ulBlockCount > EplDllkCalInstance_g.m_Statistics.m_ulMaxTxFrameCountGen)
1240 EplDllkCalInstance_g.m_Statistics.m_ulMaxTxFrameCountGen = ulBlockCount;
1243 #endif
1245 // post event to DLL
1246 Priority = kEplDllAsyncReqPrioGeneric;
1247 Event.m_EventSink = kEplEventSinkDllk;
1248 Event.m_EventType = kEplEventTypeDllkFillTx;
1249 EPL_MEMSET(&Event.m_NetTime, 0x00, sizeof(Event.m_NetTime));
1250 Event.m_pArg = &Priority;
1251 Event.m_uiSize = sizeof(Priority);
1252 Ret = EplEventkPost(&Event);
1256 #endif
1258 #endif // #if(((EPL_MODULE_INTEGRATION) & (EPL_MODULE_DLLK)) != 0)
1260 // EOF