3 static UINT
CreateSFToClassifierRuleMapping(B_UINT16 uiVcid
,B_UINT16 uiClsId
,S_SERVICEFLOW_TABLE
*psServiceFlowTable
,S_PHS_RULE
*psPhsRule
,B_UINT8 u8AssociatedPHSI
);
5 static UINT
CreateClassiferToPHSRuleMapping(B_UINT16 uiVcid
,B_UINT16 uiClsId
,S_SERVICEFLOW_ENTRY
*pstServiceFlowEntry
,S_PHS_RULE
*psPhsRule
,B_UINT8 u8AssociatedPHSI
);
7 static UINT
CreateClassifierPHSRule(B_UINT16 uiClsId
,S_CLASSIFIER_TABLE
*psaClassifiertable
,S_PHS_RULE
*psPhsRule
,E_CLASSIFIER_ENTRY_CONTEXT eClsContext
,B_UINT8 u8AssociatedPHSI
);
9 static UINT
UpdateClassifierPHSRule(B_UINT16 uiClsId
,S_CLASSIFIER_ENTRY
*pstClassifierEntry
,S_CLASSIFIER_TABLE
*psaClassifiertable
,S_PHS_RULE
*psPhsRule
,B_UINT8 u8AssociatedPHSI
);
11 static BOOLEAN
ValidatePHSRuleComplete(S_PHS_RULE
*psPhsRule
);
13 static BOOLEAN
DerefPhsRule(B_UINT16 uiClsId
,S_CLASSIFIER_TABLE
*psaClassifiertable
,S_PHS_RULE
*pstPhsRule
);
15 static UINT
GetClassifierEntry(S_CLASSIFIER_TABLE
*pstClassifierTable
,B_UINT32 uiClsid
,E_CLASSIFIER_ENTRY_CONTEXT eClsContext
, S_CLASSIFIER_ENTRY
**ppstClassifierEntry
);
17 static UINT
GetPhsRuleEntry(S_CLASSIFIER_TABLE
*pstClassifierTable
,B_UINT32 uiPHSI
,E_CLASSIFIER_ENTRY_CONTEXT eClsContext
,S_PHS_RULE
**ppstPhsRule
);
19 static void free_phs_serviceflow_rules(S_SERVICEFLOW_TABLE
*psServiceFlowRulesTable
);
21 static int phs_compress(S_PHS_RULE
*phs_members
,unsigned char *in_buf
,
22 unsigned char *out_buf
,unsigned int *header_size
,UINT
*new_header_size
);
25 static int verify_suppress_phsf(unsigned char *in_buffer
,unsigned char *out_buffer
,
26 unsigned char *phsf
,unsigned char *phsm
,unsigned int phss
,unsigned int phsv
,UINT
*new_header_size
);
28 static int phs_decompress(unsigned char *in_buf
,unsigned char *out_buf
,\
29 S_PHS_RULE
*phs_rules
,UINT
*header_size
);
32 static ULONG
PhsCompress(void* pvContext
,
38 UINT
*pNewHeaderSize
);
40 static ULONG
PhsDeCompress(void* pvContext
,
45 UINT
*pOutHeaderSize
);
55 Description: This routine handle PHS(Payload Header Suppression for Tx path.
56 It extracts a fragment of the NDIS_PACKET containing the header
57 to be suppressed.It then supresses the header by invoking PHS exported compress routine.
58 The header data after supression is copied back to the NDIS_PACKET.
61 Input parameters: IN PMINI_ADAPTER Adapter - Miniport Adapter Context
62 IN Packet - NDIS packet containing data to be transmitted
63 IN USHORT Vcid - vcid pertaining to connection on which the packet is being sent.Used to
64 identify PHS rule to be applied.
65 B_UINT16 uiClassifierRuleID - Classifier Rule ID
66 BOOLEAN bHeaderSuppressionEnabled - indicates if header suprression is enabled for SF.
68 Return: STATUS_SUCCESS - If the send was successful.
69 Other - If an error occured.
72 int PHSTransmit(PMINI_ADAPTER Adapter
,
73 struct sk_buff
**pPacket
,
75 B_UINT16 uiClassifierRuleID
,
76 BOOLEAN bHeaderSuppressionEnabled
,
82 UINT unPHSPktHdrBytesCopied
= 0;
83 UINT unPhsOldHdrSize
= 0;
84 UINT unPHSNewPktHeaderLen
= 0;
85 /* Pointer to PHS IN Hdr Buffer */
86 PUCHAR pucPHSPktHdrInBuf
=
87 Adapter
->stPhsTxContextInfo
.ucaHdrSupressionInBuf
;
88 /* Pointer to PHS OUT Hdr Buffer */
89 PUCHAR pucPHSPktHdrOutBuf
=
90 Adapter
->stPhsTxContextInfo
.ucaHdrSupressionOutBuf
;
95 UINT numBytesCompressed
= 0;
96 struct sk_buff
*newPacket
= NULL
;
97 struct sk_buff
*Packet
= *pPacket
;
99 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
, "In PHSTransmit");
102 BytesToRemove
=ETH_HLEN
;
104 Accumulate the header upto the size we support supression
108 usPacketType
=((struct ethhdr
*)(Packet
->data
))->h_proto
;
111 pucPHSPktHdrInBuf
= Packet
->data
+ BytesToRemove
;
112 //considering data after ethernet header
113 if((*PacketLen
- BytesToRemove
) < MAX_PHS_LENGTHS
)
116 unPHSPktHdrBytesCopied
= (*PacketLen
- BytesToRemove
);
120 unPHSPktHdrBytesCopied
= MAX_PHS_LENGTHS
;
123 if( (unPHSPktHdrBytesCopied
> 0 ) &&
124 (unPHSPktHdrBytesCopied
<= MAX_PHS_LENGTHS
))
128 // Step 2 Supress Header using PHS and fill into intermediate ucaPHSPktHdrOutBuf.
129 // Suppress only if IP Header and PHS Enabled For the Service Flow
130 if(((usPacketType
== ETHERNET_FRAMETYPE_IPV4
) ||
131 (usPacketType
== ETHERNET_FRAMETYPE_IPV6
)) &&
132 (bHeaderSuppressionEnabled
))
134 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"\nTrying to PHS Compress Using Classifier rule 0x%X",uiClassifierRuleID
);
137 unPHSNewPktHeaderLen
= unPHSPktHdrBytesCopied
;
138 ulPhsStatus
= PhsCompress(&Adapter
->stBCMPhsContext
,
144 &unPHSNewPktHeaderLen
);
145 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"\nPHS Old header Size : %d New Header Size %d\n",unPhsOldHdrSize
,unPHSNewPktHeaderLen
);
147 if(unPHSNewPktHeaderLen
== unPhsOldHdrSize
)
149 if( ulPhsStatus
== STATUS_PHS_COMPRESSED
)
150 bPHSI
= *pucPHSPktHdrOutBuf
;
151 ulPhsStatus
= STATUS_PHS_NOCOMPRESSION
;
154 if( ulPhsStatus
== STATUS_PHS_COMPRESSED
)
156 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"PHS Sending packet Compressed");
158 if(skb_cloned(Packet
))
160 newPacket
= skb_copy(Packet
, GFP_ATOMIC
);
162 if(newPacket
== NULL
)
163 return STATUS_FAILURE
;
165 dev_kfree_skb(Packet
);
166 *pPacket
= Packet
= newPacket
;
167 pucPHSPktHdrInBuf
= Packet
->data
+ BytesToRemove
;
170 numBytesCompressed
= unPhsOldHdrSize
- (unPHSNewPktHeaderLen
+PHSI_LEN
);
172 memcpy(pucPHSPktHdrInBuf
+ numBytesCompressed
, pucPHSPktHdrOutBuf
, unPHSNewPktHeaderLen
+ PHSI_LEN
);
173 memcpy(Packet
->data
+ numBytesCompressed
, Packet
->data
, BytesToRemove
);
174 skb_pull(Packet
, numBytesCompressed
);
176 return STATUS_SUCCESS
;
181 //if one byte headroom is not available, increase it through skb_cow
182 if(!(skb_headroom(Packet
) > 0))
184 if(skb_cow(Packet
, 1))
186 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_PRINTK
, 0, 0, "SKB Cow Failed\n");
187 return STATUS_FAILURE
;
192 // CAUTION: The MAC Header is getting corrupted here for IP CS - can be saved by copying 14 Bytes. not needed .... hence corrupting it.
193 *(Packet
->data
+ BytesToRemove
) = bPHSI
;
194 return STATUS_SUCCESS
;
199 if(!bHeaderSuppressionEnabled
)
201 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"\nHeader Suppression Disabled For SF: No PHS\n");
204 return STATUS_SUCCESS
;
208 //BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, PHS_SEND, DBG_LVL_ALL,"PHSTransmit : Dumping data packet After PHS");
209 return STATUS_SUCCESS
;
212 int PHSReceive(PMINI_ADAPTER Adapter
,
214 struct sk_buff
*packet
,
216 UCHAR
*pucEthernetHdr
,
217 UINT bHeaderSuppressionEnabled
)
219 u32 nStandardPktHdrLen
= 0;
220 u32 nTotalsupressedPktHdrBytes
= 0;
222 PUCHAR pucInBuff
= NULL
;
223 UINT TotalBytesAdded
= 0;
224 if(!bHeaderSuppressionEnabled
)
226 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_RECEIVE
,DBG_LVL_ALL
,"\nPhs Disabled for incoming packet");
230 pucInBuff
= packet
->data
;
232 //Restore PHS suppressed header
233 nStandardPktHdrLen
= packet
->len
;
234 ulPhsStatus
= PhsDeCompress(&Adapter
->stBCMPhsContext
,
237 Adapter
->ucaPHSPktRestoreBuf
,
238 &nTotalsupressedPktHdrBytes
,
239 &nStandardPktHdrLen
);
241 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_RECEIVE
,DBG_LVL_ALL
,"\nSupressed PktHdrLen : 0x%x Restored PktHdrLen : 0x%x",
242 nTotalsupressedPktHdrBytes
,nStandardPktHdrLen
);
244 if(ulPhsStatus
!= STATUS_PHS_COMPRESSED
)
247 return STATUS_SUCCESS
;
251 TotalBytesAdded
= nStandardPktHdrLen
- nTotalsupressedPktHdrBytes
- PHSI_LEN
;
254 if(skb_headroom(packet
) >= (SKB_RESERVE_ETHERNET_HEADER
+ TotalBytesAdded
))
255 skb_push(packet
, TotalBytesAdded
);
258 if(skb_cow(packet
, skb_headroom(packet
) + TotalBytesAdded
))
260 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_PRINTK
, 0, 0, "cow failed in receive\n");
261 return STATUS_FAILURE
;
264 skb_push(packet
, TotalBytesAdded
);
268 memcpy(packet
->data
, Adapter
->ucaPHSPktRestoreBuf
, nStandardPktHdrLen
);
271 return STATUS_SUCCESS
;
274 void DumpFullPacket(UCHAR
*pBuf
,UINT nPktLen
)
276 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
277 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_TX
, IPV4_DBG
, DBG_LVL_ALL
,"Dumping Data Packet");
278 BCM_DEBUG_PRINT_BUFFER(Adapter
,DBG_TYPE_TX
, IPV4_DBG
, DBG_LVL_ALL
,pBuf
,nPktLen
);
281 //-----------------------------------------------------------------------------
282 // Procedure: phs_init
284 // Description: This routine is responsible for allocating memory for classifier and
288 // pPhsdeviceExtension - ptr to Device extension containing PHS Classifier rules and PHS Rules , RX, TX buffer etc
291 // TRUE(1) -If allocation of memory was success full.
292 // FALSE -If allocation of memory fails.
293 //-----------------------------------------------------------------------------
294 int phs_init(PPHS_DEVICE_EXTENSION pPhsdeviceExtension
,PMINI_ADAPTER Adapter
)
297 S_SERVICEFLOW_TABLE
*pstServiceFlowTable
;
298 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "\nPHS:phs_init function ");
300 if(pPhsdeviceExtension
->pstServiceFlowPhsRulesTable
)
303 pPhsdeviceExtension
->pstServiceFlowPhsRulesTable
=
304 kzalloc(sizeof(S_SERVICEFLOW_TABLE
), GFP_KERNEL
);
306 if(!pPhsdeviceExtension
->pstServiceFlowPhsRulesTable
)
308 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "\nAllocation ServiceFlowPhsRulesTable failed");
312 pstServiceFlowTable
= pPhsdeviceExtension
->pstServiceFlowPhsRulesTable
;
313 for(i
=0;i
<MAX_SERVICEFLOWS
;i
++)
315 S_SERVICEFLOW_ENTRY sServiceFlow
= pstServiceFlowTable
->stSFList
[i
];
316 sServiceFlow
.pstClassifierTable
= kzalloc(sizeof(S_CLASSIFIER_TABLE
), GFP_KERNEL
);
317 if(!sServiceFlow
.pstClassifierTable
)
319 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "\nAllocation failed");
320 free_phs_serviceflow_rules(pPhsdeviceExtension
->
321 pstServiceFlowPhsRulesTable
);
322 pPhsdeviceExtension
->pstServiceFlowPhsRulesTable
= NULL
;
327 pPhsdeviceExtension
->CompressedTxBuffer
= kmalloc(PHS_BUFFER_SIZE
, GFP_KERNEL
);
329 if(pPhsdeviceExtension
->CompressedTxBuffer
== NULL
)
331 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "\nAllocation failed");
332 free_phs_serviceflow_rules(pPhsdeviceExtension
->pstServiceFlowPhsRulesTable
);
333 pPhsdeviceExtension
->pstServiceFlowPhsRulesTable
= NULL
;
337 pPhsdeviceExtension
->UnCompressedRxBuffer
= kmalloc(PHS_BUFFER_SIZE
, GFP_KERNEL
);
338 if(pPhsdeviceExtension
->UnCompressedRxBuffer
== NULL
)
340 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "\nAllocation failed");
341 kfree(pPhsdeviceExtension
->CompressedTxBuffer
);
342 free_phs_serviceflow_rules(pPhsdeviceExtension
->pstServiceFlowPhsRulesTable
);
343 pPhsdeviceExtension
->pstServiceFlowPhsRulesTable
= NULL
;
349 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "\n phs_init Successfull");
350 return STATUS_SUCCESS
;
354 int PhsCleanup(IN PPHS_DEVICE_EXTENSION pPHSDeviceExt
)
356 if(pPHSDeviceExt
->pstServiceFlowPhsRulesTable
)
358 free_phs_serviceflow_rules(pPHSDeviceExt
->pstServiceFlowPhsRulesTable
);
359 pPHSDeviceExt
->pstServiceFlowPhsRulesTable
= NULL
;
362 kfree(pPHSDeviceExt
->CompressedTxBuffer
);
363 pPHSDeviceExt
->CompressedTxBuffer
= NULL
;
365 kfree(pPHSDeviceExt
->UnCompressedRxBuffer
);
366 pPHSDeviceExt
->UnCompressedRxBuffer
= NULL
;
375 PhsUpdateClassifierRule
378 Exported function to add or modify a PHS Rule.
381 IN void* pvContext - PHS Driver Specific Context
382 IN B_UINT16 uiVcid - The Service Flow ID for which the PHS rule applies
383 IN B_UINT16 uiClsId - The Classifier ID within the Service Flow for which the PHS rule applies.
384 IN S_PHS_RULE *psPhsRule - The PHS Rule strcuture to be added to the PHS Rule table.
392 ULONG
PhsUpdateClassifierRule(IN
void* pvContext
,
394 IN B_UINT16 uiClsId
,
395 IN S_PHS_RULE
*psPhsRule
,
396 IN B_UINT8 u8AssociatedPHSI
)
400 S_SERVICEFLOW_ENTRY
*pstServiceFlowEntry
= NULL
;
401 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
405 PPHS_DEVICE_EXTENSION pDeviceExtension
= (PPHS_DEVICE_EXTENSION
)pvContext
;
407 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
,"PHS With Corr2 Changes \n");
409 if(pDeviceExtension
== NULL
)
411 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
,"Invalid Device Extension\n");
412 return ERR_PHS_INVALID_DEVICE_EXETENSION
;
416 if(u8AssociatedPHSI
== 0)
418 return ERR_PHS_INVALID_PHS_RULE
;
421 /* Retrieve the SFID Entry Index for requested Service Flow */
423 nSFIndex
= GetServiceFlowEntry(pDeviceExtension
->pstServiceFlowPhsRulesTable
,
424 uiVcid
,&pstServiceFlowEntry
);
426 if(nSFIndex
== PHS_INVALID_TABLE_INDEX
)
428 /* This is a new SF. Create a mapping entry for this */
429 lStatus
= CreateSFToClassifierRuleMapping(uiVcid
, uiClsId
,
430 pDeviceExtension
->pstServiceFlowPhsRulesTable
, psPhsRule
, u8AssociatedPHSI
);
434 /* SF already Exists Add PHS Rule to existing SF */
435 lStatus
= CreateClassiferToPHSRuleMapping(uiVcid
, uiClsId
,
436 pstServiceFlowEntry
, psPhsRule
, u8AssociatedPHSI
);
445 Deletes the specified phs Rule within Vcid
448 IN void* pvContext - PHS Driver Specific Context
449 IN B_UINT16 uiVcid - The Service Flow ID for which the PHS rule applies
450 IN B_UINT8 u8PHSI - the PHS Index identifying PHS rule to be deleted.
459 ULONG
PhsDeletePHSRule(IN
void* pvContext
,IN B_UINT16 uiVcid
,IN B_UINT8 u8PHSI
)
462 UINT nSFIndex
=0, nClsidIndex
=0 ;
463 S_SERVICEFLOW_ENTRY
*pstServiceFlowEntry
= NULL
;
464 S_CLASSIFIER_TABLE
*pstClassifierRulesTable
= NULL
;
465 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
468 PPHS_DEVICE_EXTENSION pDeviceExtension
= (PPHS_DEVICE_EXTENSION
)pvContext
;
470 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "======>\n");
475 //Retrieve the SFID Entry Index for requested Service Flow
476 nSFIndex
= GetServiceFlowEntry(pDeviceExtension
477 ->pstServiceFlowPhsRulesTable
,uiVcid
,&pstServiceFlowEntry
);
479 if(nSFIndex
== PHS_INVALID_TABLE_INDEX
)
481 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "SFID Match Failed\n");
482 return ERR_SF_MATCH_FAIL
;
485 pstClassifierRulesTable
=pstServiceFlowEntry
->pstClassifierTable
;
486 if(pstClassifierRulesTable
)
488 for(nClsidIndex
=0;nClsidIndex
<MAX_PHSRULE_PER_SF
;nClsidIndex
++)
490 if(pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
].bUsed
&& pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
].pstPhsRule
)
492 if(pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
].pstPhsRule
->u8PHSI
== u8PHSI
) {
493 if(pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
].pstPhsRule
->u8RefCnt
)
494 pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
].pstPhsRule
->u8RefCnt
--;
495 if(0 == pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
].pstPhsRule
->u8RefCnt
)
496 kfree(pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
].pstPhsRule
);
497 memset(&pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
], 0,
498 sizeof(S_CLASSIFIER_ENTRY
));
509 PhsDeleteClassifierRule
512 Exported function to Delete a PHS Rule for the SFID,CLSID Pair.
515 IN void* pvContext - PHS Driver Specific Context
516 IN B_UINT16 uiVcid - The Service Flow ID for which the PHS rule applies
517 IN B_UINT16 uiClsId - The Classifier ID within the Service Flow for which the PHS rule applies.
525 ULONG
PhsDeleteClassifierRule(IN
void* pvContext
,IN B_UINT16 uiVcid
,IN B_UINT16 uiClsId
)
528 UINT nSFIndex
=0, nClsidIndex
=0 ;
529 S_SERVICEFLOW_ENTRY
*pstServiceFlowEntry
= NULL
;
530 S_CLASSIFIER_ENTRY
*pstClassifierEntry
= NULL
;
531 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
532 PPHS_DEVICE_EXTENSION pDeviceExtension
= (PPHS_DEVICE_EXTENSION
)pvContext
;
536 //Retrieve the SFID Entry Index for requested Service Flow
537 nSFIndex
= GetServiceFlowEntry(pDeviceExtension
538 ->pstServiceFlowPhsRulesTable
, uiVcid
, &pstServiceFlowEntry
);
539 if(nSFIndex
== PHS_INVALID_TABLE_INDEX
)
541 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
,"SFID Match Failed\n");
542 return ERR_SF_MATCH_FAIL
;
545 nClsidIndex
= GetClassifierEntry(pstServiceFlowEntry
->pstClassifierTable
,
546 uiClsId
, eActiveClassifierRuleContext
, &pstClassifierEntry
);
547 if((nClsidIndex
!= PHS_INVALID_TABLE_INDEX
) && (!pstClassifierEntry
->bUnclassifiedPHSRule
))
549 if(pstClassifierEntry
->pstPhsRule
)
551 if(pstClassifierEntry
->pstPhsRule
->u8RefCnt
)
552 pstClassifierEntry
->pstPhsRule
->u8RefCnt
--;
553 if(0==pstClassifierEntry
->pstPhsRule
->u8RefCnt
)
554 kfree(pstClassifierEntry
->pstPhsRule
);
557 memset(pstClassifierEntry
, 0, sizeof(S_CLASSIFIER_ENTRY
));
560 nClsidIndex
= GetClassifierEntry(pstServiceFlowEntry
->pstClassifierTable
,
561 uiClsId
,eOldClassifierRuleContext
,&pstClassifierEntry
);
563 if((nClsidIndex
!= PHS_INVALID_TABLE_INDEX
) && (!pstClassifierEntry
->bUnclassifiedPHSRule
))
565 kfree(pstClassifierEntry
->pstPhsRule
);
566 memset(pstClassifierEntry
, 0, sizeof(S_CLASSIFIER_ENTRY
));
576 Exported function to Delete a all PHS Rules for the SFID.
579 IN void* pvContext - PHS Driver Specific Context
580 IN B_UINT16 uiVcid - The Service Flow ID for which the PHS rules need to be deleted
588 ULONG
PhsDeleteSFRules(IN
void* pvContext
,IN B_UINT16 uiVcid
)
592 UINT nSFIndex
=0, nClsidIndex
=0 ;
593 S_SERVICEFLOW_ENTRY
*pstServiceFlowEntry
= NULL
;
594 S_CLASSIFIER_TABLE
*pstClassifierRulesTable
= NULL
;
595 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
596 PPHS_DEVICE_EXTENSION pDeviceExtension
= (PPHS_DEVICE_EXTENSION
)pvContext
;
597 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
,"====> \n");
601 //Retrieve the SFID Entry Index for requested Service Flow
602 nSFIndex
= GetServiceFlowEntry(pDeviceExtension
->pstServiceFlowPhsRulesTable
,
603 uiVcid
,&pstServiceFlowEntry
);
604 if(nSFIndex
== PHS_INVALID_TABLE_INDEX
)
606 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "SFID Match Failed\n");
607 return ERR_SF_MATCH_FAIL
;
610 pstClassifierRulesTable
=pstServiceFlowEntry
->pstClassifierTable
;
611 if(pstClassifierRulesTable
)
613 for(nClsidIndex
=0;nClsidIndex
<MAX_PHSRULE_PER_SF
;nClsidIndex
++)
615 if(pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
].pstPhsRule
)
617 if(pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
]
618 .pstPhsRule
->u8RefCnt
)
619 pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
]
620 .pstPhsRule
->u8RefCnt
--;
621 if(0==pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
]
622 .pstPhsRule
->u8RefCnt
)
623 kfree(pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
].pstPhsRule
);
624 pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
]
627 memset(&pstClassifierRulesTable
->stActivePhsRulesList
[nClsidIndex
], 0, sizeof(S_CLASSIFIER_ENTRY
));
628 if(pstClassifierRulesTable
->stOldPhsRulesList
[nClsidIndex
].pstPhsRule
)
630 if(pstClassifierRulesTable
->stOldPhsRulesList
[nClsidIndex
]
631 .pstPhsRule
->u8RefCnt
)
632 pstClassifierRulesTable
->stOldPhsRulesList
[nClsidIndex
]
633 .pstPhsRule
->u8RefCnt
--;
634 if(0 == pstClassifierRulesTable
->stOldPhsRulesList
[nClsidIndex
]
635 .pstPhsRule
->u8RefCnt
)
636 kfree(pstClassifierRulesTable
637 ->stOldPhsRulesList
[nClsidIndex
].pstPhsRule
);
638 pstClassifierRulesTable
->stOldPhsRulesList
[nClsidIndex
]
641 memset(&pstClassifierRulesTable
->stOldPhsRulesList
[nClsidIndex
], 0, sizeof(S_CLASSIFIER_ENTRY
));
644 pstServiceFlowEntry
->bUsed
= FALSE
;
645 pstServiceFlowEntry
->uiVcid
= 0;
657 Exported function to compress the data using PHS.
660 IN void* pvContext - PHS Driver Specific Context.
661 IN B_UINT16 uiVcid - The Service Flow ID to which current packet header compression applies.
662 IN UINT uiClsId - The Classifier ID to which current packet header compression applies.
663 IN void *pvInputBuffer - The Input buffer containg packet header data
664 IN void *pvOutputBuffer - The output buffer returned by this function after PHS
665 IN UINT *pOldHeaderSize - The actual size of the header before PHS
666 IN UINT *pNewHeaderSize - The new size of the header after applying PHS
674 ULONG
PhsCompress(IN
void* pvContext
,
677 IN
void *pvInputBuffer
,
678 OUT
void *pvOutputBuffer
,
679 OUT UINT
*pOldHeaderSize
,
680 OUT UINT
*pNewHeaderSize
)
682 UINT nSFIndex
=0, nClsidIndex
=0 ;
683 S_SERVICEFLOW_ENTRY
*pstServiceFlowEntry
= NULL
;
684 S_CLASSIFIER_ENTRY
*pstClassifierEntry
= NULL
;
685 S_PHS_RULE
*pstPhsRule
= NULL
;
687 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
691 PPHS_DEVICE_EXTENSION pDeviceExtension
= (PPHS_DEVICE_EXTENSION
)pvContext
;
694 if(pDeviceExtension
== NULL
)
696 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"Invalid Device Extension\n");
697 lStatus
= STATUS_PHS_NOCOMPRESSION
;
702 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"Suppressing header \n");
705 //Retrieve the SFID Entry Index for requested Service Flow
706 nSFIndex
= GetServiceFlowEntry(pDeviceExtension
->pstServiceFlowPhsRulesTable
,
707 uiVcid
,&pstServiceFlowEntry
);
708 if(nSFIndex
== PHS_INVALID_TABLE_INDEX
)
710 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"SFID Match Failed\n");
711 lStatus
= STATUS_PHS_NOCOMPRESSION
;
715 nClsidIndex
= GetClassifierEntry(pstServiceFlowEntry
->pstClassifierTable
,
716 uiClsId
,eActiveClassifierRuleContext
,&pstClassifierEntry
);
718 if(nClsidIndex
== PHS_INVALID_TABLE_INDEX
)
720 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"No PHS Rule Defined For Classifier\n");
721 lStatus
= STATUS_PHS_NOCOMPRESSION
;
726 //get rule from SF id,Cls ID pair and proceed
727 pstPhsRule
= pstClassifierEntry
->pstPhsRule
;
729 if(!ValidatePHSRuleComplete(pstPhsRule
))
731 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
,"PHS Rule Defined For Classifier But Not Complete\n");
732 lStatus
= STATUS_PHS_NOCOMPRESSION
;
737 lStatus
= phs_compress(pstPhsRule
,(PUCHAR
)pvInputBuffer
,
738 (PUCHAR
)pvOutputBuffer
, pOldHeaderSize
,pNewHeaderSize
);
740 if(lStatus
== STATUS_PHS_COMPRESSED
)
742 pstPhsRule
->PHSModifiedBytes
+= *pOldHeaderSize
- *pNewHeaderSize
- 1;
743 pstPhsRule
->PHSModifiedNumPackets
++;
746 pstPhsRule
->PHSErrorNumPackets
++;
755 Exported function to restore the packet header in Rx path.
758 IN void* pvContext - PHS Driver Specific Context.
759 IN B_UINT16 uiVcid - The Service Flow ID to which current packet header restoration applies.
760 IN void *pvInputBuffer - The Input buffer containg suppressed packet header data
761 OUT void *pvOutputBuffer - The output buffer returned by this function after restoration
762 OUT UINT *pHeaderSize - The packet header size after restoration is returned in this parameter.
770 ULONG
PhsDeCompress(IN
void* pvContext
,
772 IN
void *pvInputBuffer
,
773 OUT
void *pvOutputBuffer
,
774 OUT UINT
*pInHeaderSize
,
775 OUT UINT
*pOutHeaderSize
)
777 UINT nSFIndex
=0, nPhsRuleIndex
=0 ;
778 S_SERVICEFLOW_ENTRY
*pstServiceFlowEntry
= NULL
;
779 S_PHS_RULE
*pstPhsRule
= NULL
;
781 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
782 PPHS_DEVICE_EXTENSION pDeviceExtension
=
783 (PPHS_DEVICE_EXTENSION
)pvContext
;
787 if(pDeviceExtension
== NULL
)
789 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_RECEIVE
,DBG_LVL_ALL
,"Invalid Device Extension\n");
790 return ERR_PHS_INVALID_DEVICE_EXETENSION
;
793 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_RECEIVE
,DBG_LVL_ALL
,"Restoring header\n");
795 phsi
= *((unsigned char *)(pvInputBuffer
));
796 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_RECEIVE
,DBG_LVL_ALL
,"PHSI To Be Used For restore : %x\n",phsi
);
797 if(phsi
== UNCOMPRESSED_PACKET
)
799 return STATUS_PHS_NOCOMPRESSION
;
802 //Retrieve the SFID Entry Index for requested Service Flow
803 nSFIndex
= GetServiceFlowEntry(pDeviceExtension
->pstServiceFlowPhsRulesTable
,
804 uiVcid
,&pstServiceFlowEntry
);
805 if(nSFIndex
== PHS_INVALID_TABLE_INDEX
)
807 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_RECEIVE
,DBG_LVL_ALL
,"SFID Match Failed During Lookup\n");
808 return ERR_SF_MATCH_FAIL
;
811 nPhsRuleIndex
= GetPhsRuleEntry(pstServiceFlowEntry
->pstClassifierTable
,phsi
,
812 eActiveClassifierRuleContext
,&pstPhsRule
);
813 if(nPhsRuleIndex
== PHS_INVALID_TABLE_INDEX
)
815 //Phs Rule does not exist in active rules table. Lets try in the old rules table.
816 nPhsRuleIndex
= GetPhsRuleEntry(pstServiceFlowEntry
->pstClassifierTable
,
817 phsi
,eOldClassifierRuleContext
,&pstPhsRule
);
818 if(nPhsRuleIndex
== PHS_INVALID_TABLE_INDEX
)
820 return ERR_PHSRULE_MATCH_FAIL
;
825 *pInHeaderSize
= phs_decompress((PUCHAR
)pvInputBuffer
,
826 (PUCHAR
)pvOutputBuffer
,pstPhsRule
,pOutHeaderSize
);
828 pstPhsRule
->PHSModifiedBytes
+= *pOutHeaderSize
- *pInHeaderSize
- 1;
830 pstPhsRule
->PHSModifiedNumPackets
++;
831 return STATUS_PHS_COMPRESSED
;
835 //-----------------------------------------------------------------------------
836 // Procedure: free_phs_serviceflow_rules
838 // Description: This routine is responsible for freeing memory allocated for PHS rules.
841 // rules - ptr to S_SERVICEFLOW_TABLE structure.
844 // Does not return any value.
845 //-----------------------------------------------------------------------------
847 static void free_phs_serviceflow_rules(S_SERVICEFLOW_TABLE
*psServiceFlowRulesTable
)
850 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
852 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "=======>\n");
853 if(psServiceFlowRulesTable
)
855 for(i
=0;i
<MAX_SERVICEFLOWS
;i
++)
857 S_SERVICEFLOW_ENTRY stServiceFlowEntry
=
858 psServiceFlowRulesTable
->stSFList
[i
];
859 S_CLASSIFIER_TABLE
*pstClassifierRulesTable
=
860 stServiceFlowEntry
.pstClassifierTable
;
862 if(pstClassifierRulesTable
)
864 for(j
=0;j
<MAX_PHSRULE_PER_SF
;j
++)
866 if(pstClassifierRulesTable
->stActivePhsRulesList
[j
].pstPhsRule
)
868 if(pstClassifierRulesTable
->stActivePhsRulesList
[j
].pstPhsRule
870 pstClassifierRulesTable
->stActivePhsRulesList
[j
].pstPhsRule
872 if(0==pstClassifierRulesTable
->stActivePhsRulesList
[j
].pstPhsRule
874 kfree(pstClassifierRulesTable
->stActivePhsRulesList
[j
].pstPhsRule
);
875 pstClassifierRulesTable
->stActivePhsRulesList
[j
].pstPhsRule
= NULL
;
877 if(pstClassifierRulesTable
->stOldPhsRulesList
[j
].pstPhsRule
)
879 if(pstClassifierRulesTable
->stOldPhsRulesList
[j
].pstPhsRule
881 pstClassifierRulesTable
->stOldPhsRulesList
[j
].pstPhsRule
883 if(0==pstClassifierRulesTable
->stOldPhsRulesList
[j
].pstPhsRule
885 kfree(pstClassifierRulesTable
->stOldPhsRulesList
[j
].pstPhsRule
);
886 pstClassifierRulesTable
->stOldPhsRulesList
[j
].pstPhsRule
= NULL
;
889 kfree(pstClassifierRulesTable
);
890 stServiceFlowEntry
.pstClassifierTable
= pstClassifierRulesTable
= NULL
;
895 kfree(psServiceFlowRulesTable
);
896 psServiceFlowRulesTable
= NULL
;
901 static BOOLEAN
ValidatePHSRuleComplete(IN S_PHS_RULE
*psPhsRule
)
905 if(!psPhsRule
->u8PHSI
)
911 if(!psPhsRule
->u8PHSS
)
917 //Check if PHSF is defines for the PHS Rule
918 if(!psPhsRule
->u8PHSFLength
) // If any part of PHSF is valid then Rule contains valid PHSF
930 UINT
GetServiceFlowEntry(IN S_SERVICEFLOW_TABLE
*psServiceFlowTable
,
931 IN B_UINT16 uiVcid
,S_SERVICEFLOW_ENTRY
**ppstServiceFlowEntry
)
934 for(i
=0;i
<MAX_SERVICEFLOWS
;i
++)
936 if(psServiceFlowTable
->stSFList
[i
].bUsed
)
938 if(psServiceFlowTable
->stSFList
[i
].uiVcid
== uiVcid
)
940 *ppstServiceFlowEntry
= &psServiceFlowTable
->stSFList
[i
];
946 *ppstServiceFlowEntry
= NULL
;
947 return PHS_INVALID_TABLE_INDEX
;
951 UINT
GetClassifierEntry(IN S_CLASSIFIER_TABLE
*pstClassifierTable
,
952 IN B_UINT32 uiClsid
,E_CLASSIFIER_ENTRY_CONTEXT eClsContext
,
953 OUT S_CLASSIFIER_ENTRY
**ppstClassifierEntry
)
956 S_CLASSIFIER_ENTRY
*psClassifierRules
= NULL
;
957 for(i
=0;i
<MAX_PHSRULE_PER_SF
;i
++)
960 if(eClsContext
== eActiveClassifierRuleContext
)
962 psClassifierRules
= &pstClassifierTable
->stActivePhsRulesList
[i
];
966 psClassifierRules
= &pstClassifierTable
->stOldPhsRulesList
[i
];
969 if(psClassifierRules
->bUsed
)
971 if(psClassifierRules
->uiClassifierRuleId
== uiClsid
)
973 *ppstClassifierEntry
= psClassifierRules
;
980 *ppstClassifierEntry
= NULL
;
981 return PHS_INVALID_TABLE_INDEX
;
984 static UINT
GetPhsRuleEntry(IN S_CLASSIFIER_TABLE
*pstClassifierTable
,
985 IN B_UINT32 uiPHSI
,E_CLASSIFIER_ENTRY_CONTEXT eClsContext
,
986 OUT S_PHS_RULE
**ppstPhsRule
)
989 S_CLASSIFIER_ENTRY
*pstClassifierRule
= NULL
;
990 for(i
=0;i
<MAX_PHSRULE_PER_SF
;i
++)
992 if(eClsContext
== eActiveClassifierRuleContext
)
994 pstClassifierRule
= &pstClassifierTable
->stActivePhsRulesList
[i
];
998 pstClassifierRule
= &pstClassifierTable
->stOldPhsRulesList
[i
];
1000 if(pstClassifierRule
->bUsed
)
1002 if(pstClassifierRule
->u8PHSI
== uiPHSI
)
1004 *ppstPhsRule
= pstClassifierRule
->pstPhsRule
;
1011 *ppstPhsRule
= NULL
;
1012 return PHS_INVALID_TABLE_INDEX
;
1015 UINT
CreateSFToClassifierRuleMapping(IN B_UINT16 uiVcid
,IN B_UINT16 uiClsId
,
1016 IN S_SERVICEFLOW_TABLE
*psServiceFlowTable
,S_PHS_RULE
*psPhsRule
,
1017 B_UINT8 u8AssociatedPHSI
)
1020 S_CLASSIFIER_TABLE
*psaClassifiertable
= NULL
;
1023 BOOLEAN bFreeEntryFound
=FALSE
;
1024 //Check for a free entry in SFID table
1025 for(iSfIndex
=0;iSfIndex
< MAX_SERVICEFLOWS
;iSfIndex
++)
1027 if(!psServiceFlowTable
->stSFList
[iSfIndex
].bUsed
)
1029 bFreeEntryFound
= TRUE
;
1034 if(!bFreeEntryFound
)
1035 return ERR_SFTABLE_FULL
;
1038 psaClassifiertable
= psServiceFlowTable
->stSFList
[iSfIndex
].pstClassifierTable
;
1039 uiStatus
= CreateClassifierPHSRule(uiClsId
,psaClassifiertable
,psPhsRule
,
1040 eActiveClassifierRuleContext
,u8AssociatedPHSI
);
1041 if(uiStatus
== PHS_SUCCESS
)
1043 //Add entry at free index to the SF
1044 psServiceFlowTable
->stSFList
[iSfIndex
].bUsed
= TRUE
;
1045 psServiceFlowTable
->stSFList
[iSfIndex
].uiVcid
= uiVcid
;
1052 UINT
CreateClassiferToPHSRuleMapping(IN B_UINT16 uiVcid
,
1053 IN B_UINT16 uiClsId
,IN S_SERVICEFLOW_ENTRY
*pstServiceFlowEntry
,
1054 S_PHS_RULE
*psPhsRule
,B_UINT8 u8AssociatedPHSI
)
1056 S_CLASSIFIER_ENTRY
*pstClassifierEntry
= NULL
;
1057 UINT uiStatus
=PHS_SUCCESS
;
1058 UINT nClassifierIndex
= 0;
1059 S_CLASSIFIER_TABLE
*psaClassifiertable
= NULL
;
1060 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
1061 psaClassifiertable
= pstServiceFlowEntry
->pstClassifierTable
;
1063 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "==>");
1065 /* Check if the supplied Classifier already exists */
1066 nClassifierIndex
=GetClassifierEntry(
1067 pstServiceFlowEntry
->pstClassifierTable
,uiClsId
,
1068 eActiveClassifierRuleContext
,&pstClassifierEntry
);
1069 if(nClassifierIndex
== PHS_INVALID_TABLE_INDEX
)
1072 The Classifier doesn't exist. So its a new classifier being added.
1073 Add new entry to associate PHS Rule to the Classifier
1076 uiStatus
= CreateClassifierPHSRule(uiClsId
,psaClassifiertable
,
1077 psPhsRule
,eActiveClassifierRuleContext
,u8AssociatedPHSI
);
1082 The Classifier exists.The PHS Rule for this classifier
1085 if(pstClassifierEntry
->u8PHSI
== psPhsRule
->u8PHSI
)
1087 if(pstClassifierEntry
->pstPhsRule
== NULL
)
1088 return ERR_PHS_INVALID_PHS_RULE
;
1091 This rule already exists if any fields are changed for this PHS
1094 /* If any part of PHSF is valid then we update PHSF */
1095 if(psPhsRule
->u8PHSFLength
)
1098 memcpy(pstClassifierEntry
->pstPhsRule
->u8PHSF
,
1099 psPhsRule
->u8PHSF
, MAX_PHS_LENGTHS
);
1101 if(psPhsRule
->u8PHSFLength
)
1104 pstClassifierEntry
->pstPhsRule
->u8PHSFLength
=
1105 psPhsRule
->u8PHSFLength
;
1107 if(psPhsRule
->u8PHSMLength
)
1110 memcpy(pstClassifierEntry
->pstPhsRule
->u8PHSM
,
1111 psPhsRule
->u8PHSM
, MAX_PHS_LENGTHS
);
1113 if(psPhsRule
->u8PHSMLength
)
1116 pstClassifierEntry
->pstPhsRule
->u8PHSMLength
=
1117 psPhsRule
->u8PHSMLength
;
1119 if(psPhsRule
->u8PHSS
)
1122 pstClassifierEntry
->pstPhsRule
->u8PHSS
= psPhsRule
->u8PHSS
;
1126 pstClassifierEntry
->pstPhsRule
->u8PHSV
= psPhsRule
->u8PHSV
;
1132 A new rule is being set for this classifier.
1134 uiStatus
=UpdateClassifierPHSRule( uiClsId
, pstClassifierEntry
,
1135 psaClassifiertable
, psPhsRule
, u8AssociatedPHSI
);
1143 static UINT
CreateClassifierPHSRule(IN B_UINT16 uiClsId
,
1144 S_CLASSIFIER_TABLE
*psaClassifiertable
,S_PHS_RULE
*psPhsRule
,
1145 E_CLASSIFIER_ENTRY_CONTEXT eClsContext
,B_UINT8 u8AssociatedPHSI
)
1147 UINT iClassifierIndex
= 0;
1148 BOOLEAN bFreeEntryFound
= FALSE
;
1149 S_CLASSIFIER_ENTRY
*psClassifierRules
= NULL
;
1150 UINT nStatus
= PHS_SUCCESS
;
1151 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
1152 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
,"Inside CreateClassifierPHSRule");
1153 if(psaClassifiertable
== NULL
)
1155 return ERR_INVALID_CLASSIFIERTABLE_FOR_SF
;
1158 if(eClsContext
== eOldClassifierRuleContext
)
1160 /* If An Old Entry for this classifier ID already exists in the
1161 old rules table replace it. */
1164 GetClassifierEntry(psaClassifiertable
, uiClsId
,
1165 eClsContext
,&psClassifierRules
);
1166 if(iClassifierIndex
!= PHS_INVALID_TABLE_INDEX
)
1169 The Classifier already exists in the old rules table
1170 Lets replace the old classifier with the new one.
1172 bFreeEntryFound
= TRUE
;
1176 if(!bFreeEntryFound
)
1179 Continue to search for a free location to add the rule
1181 for(iClassifierIndex
= 0; iClassifierIndex
<
1182 MAX_PHSRULE_PER_SF
; iClassifierIndex
++)
1184 if(eClsContext
== eActiveClassifierRuleContext
)
1187 &psaClassifiertable
->stActivePhsRulesList
[iClassifierIndex
];
1192 &psaClassifiertable
->stOldPhsRulesList
[iClassifierIndex
];
1195 if(!psClassifierRules
->bUsed
)
1197 bFreeEntryFound
= TRUE
;
1203 if(!bFreeEntryFound
)
1205 if(eClsContext
== eActiveClassifierRuleContext
)
1207 return ERR_CLSASSIFIER_TABLE_FULL
;
1211 //Lets replace the oldest rule if we are looking in old Rule table
1212 if(psaClassifiertable
->uiOldestPhsRuleIndex
>=
1215 psaClassifiertable
->uiOldestPhsRuleIndex
=0;
1218 iClassifierIndex
= psaClassifiertable
->uiOldestPhsRuleIndex
;
1220 &psaClassifiertable
->stOldPhsRulesList
[iClassifierIndex
];
1222 (psaClassifiertable
->uiOldestPhsRuleIndex
)++;
1226 if(eClsContext
== eOldClassifierRuleContext
)
1228 if(psClassifierRules
->pstPhsRule
== NULL
)
1230 psClassifierRules
->pstPhsRule
= kmalloc(sizeof(S_PHS_RULE
),GFP_KERNEL
);
1232 if(NULL
== psClassifierRules
->pstPhsRule
)
1233 return ERR_PHSRULE_MEMALLOC_FAIL
;
1236 psClassifierRules
->bUsed
= TRUE
;
1237 psClassifierRules
->uiClassifierRuleId
= uiClsId
;
1238 psClassifierRules
->u8PHSI
= psPhsRule
->u8PHSI
;
1239 psClassifierRules
->bUnclassifiedPHSRule
= psPhsRule
->bUnclassifiedPHSRule
;
1241 /* Update The PHS rule */
1242 memcpy(psClassifierRules
->pstPhsRule
,
1243 psPhsRule
, sizeof(S_PHS_RULE
));
1247 nStatus
= UpdateClassifierPHSRule(uiClsId
,psClassifierRules
,
1248 psaClassifiertable
,psPhsRule
,u8AssociatedPHSI
);
1254 static UINT
UpdateClassifierPHSRule(IN B_UINT16 uiClsId
,
1255 IN S_CLASSIFIER_ENTRY
*pstClassifierEntry
,
1256 S_CLASSIFIER_TABLE
*psaClassifiertable
,S_PHS_RULE
*psPhsRule
,
1257 B_UINT8 u8AssociatedPHSI
)
1259 S_PHS_RULE
*pstAddPhsRule
= NULL
;
1260 UINT nPhsRuleIndex
= 0;
1261 BOOLEAN bPHSRuleOrphaned
= FALSE
;
1262 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
1263 psPhsRule
->u8RefCnt
=0;
1265 /* Step 1 Deref Any Exisiting PHS Rule in this classifier Entry*/
1266 bPHSRuleOrphaned
= DerefPhsRule( uiClsId
, psaClassifiertable
,
1267 pstClassifierEntry
->pstPhsRule
);
1269 //Step 2 Search if there is a PHS Rule with u8AssociatedPHSI in Classifier table for this SF
1270 nPhsRuleIndex
=GetPhsRuleEntry(psaClassifiertable
,u8AssociatedPHSI
,
1271 eActiveClassifierRuleContext
, &pstAddPhsRule
);
1272 if(PHS_INVALID_TABLE_INDEX
== nPhsRuleIndex
)
1274 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "\nAdding New PHSRuleEntry For Classifier");
1276 if(psPhsRule
->u8PHSI
== 0)
1278 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "\nError PHSI is Zero\n");
1279 return ERR_PHS_INVALID_PHS_RULE
;
1281 //Step 2.a PHS Rule Does Not Exist .Create New PHS Rule for uiClsId
1282 if(FALSE
== bPHSRuleOrphaned
)
1284 pstClassifierEntry
->pstPhsRule
= kmalloc(sizeof(S_PHS_RULE
), GFP_KERNEL
);
1285 if(NULL
== pstClassifierEntry
->pstPhsRule
)
1287 return ERR_PHSRULE_MEMALLOC_FAIL
;
1290 memcpy(pstClassifierEntry
->pstPhsRule
, psPhsRule
, sizeof(S_PHS_RULE
));
1295 //Step 2.b PHS Rule Exists Tie uiClsId with the existing PHS Rule
1296 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_DISPATCH
, DBG_LVL_ALL
, "\nTying Classifier to Existing PHS Rule");
1297 if(bPHSRuleOrphaned
)
1299 kfree(pstClassifierEntry
->pstPhsRule
);
1300 pstClassifierEntry
->pstPhsRule
= NULL
;
1302 pstClassifierEntry
->pstPhsRule
= pstAddPhsRule
;
1305 pstClassifierEntry
->bUsed
= TRUE
;
1306 pstClassifierEntry
->u8PHSI
= pstClassifierEntry
->pstPhsRule
->u8PHSI
;
1307 pstClassifierEntry
->uiClassifierRuleId
= uiClsId
;
1308 pstClassifierEntry
->pstPhsRule
->u8RefCnt
++;
1309 pstClassifierEntry
->bUnclassifiedPHSRule
= pstClassifierEntry
->pstPhsRule
->bUnclassifiedPHSRule
;
1315 static BOOLEAN
DerefPhsRule(IN B_UINT16 uiClsId
,S_CLASSIFIER_TABLE
*psaClassifiertable
,S_PHS_RULE
*pstPhsRule
)
1317 if(pstPhsRule
==NULL
)
1319 if(pstPhsRule
->u8RefCnt
)
1320 pstPhsRule
->u8RefCnt
--;
1321 if(0==pstPhsRule
->u8RefCnt
)
1323 /*if(pstPhsRule->u8PHSI)
1324 //Store the currently active rule into the old rules list
1325 CreateClassifierPHSRule(uiClsId,psaClassifiertable,pstPhsRule,eOldClassifierRuleContext,pstPhsRule->u8PHSI);*/
1334 void DumpPhsRules(PPHS_DEVICE_EXTENSION pDeviceExtension
)
1337 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
1338 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, DBG_LVL_ALL
, "\n Dumping PHS Rules : \n");
1339 for(i
=0;i
<MAX_SERVICEFLOWS
;i
++)
1341 S_SERVICEFLOW_ENTRY stServFlowEntry
=
1342 pDeviceExtension
->pstServiceFlowPhsRulesTable
->stSFList
[i
];
1343 if(stServFlowEntry
.bUsed
)
1345 for(j
=0;j
<MAX_PHSRULE_PER_SF
;j
++)
1349 S_CLASSIFIER_ENTRY stClsEntry
;
1352 stClsEntry
= stServFlowEntry
.pstClassifierTable
->stActivePhsRulesList
[j
];
1353 if(stClsEntry
.bUsed
)
1354 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "\n Active PHS Rule : \n");
1358 stClsEntry
= stServFlowEntry
.pstClassifierTable
->stOldPhsRulesList
[j
];
1359 if(stClsEntry
.bUsed
)
1360 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "\n Old PHS Rule : \n");
1362 if(stClsEntry
.bUsed
)
1365 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, DBG_LVL_ALL
, "\n VCID : %#X",stServFlowEntry
.uiVcid
);
1366 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "\n ClassifierID : %#X",stClsEntry
.uiClassifierRuleId
);
1367 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "\n PHSRuleID : %#X",stClsEntry
.u8PHSI
);
1368 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "\n****************PHS Rule********************\n");
1369 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "\n PHSI : %#X",stClsEntry
.pstPhsRule
->u8PHSI
);
1370 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "\n PHSFLength : %#X ",stClsEntry
.pstPhsRule
->u8PHSFLength
);
1371 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "\n PHSF : ");
1372 for(k
=0;k
<stClsEntry
.pstPhsRule
->u8PHSFLength
;k
++)
1374 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "%#X ",stClsEntry
.pstPhsRule
->u8PHSF
[k
]);
1376 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "\n PHSMLength : %#X",stClsEntry
.pstPhsRule
->u8PHSMLength
);
1377 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "\n PHSM :");
1378 for(k
=0;k
<stClsEntry
.pstPhsRule
->u8PHSMLength
;k
++)
1380 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "%#X ",stClsEntry
.pstPhsRule
->u8PHSM
[k
]);
1382 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "\n PHSS : %#X ",stClsEntry
.pstPhsRule
->u8PHSS
);
1383 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, (DBG_LVL_ALL
|DBG_NO_FUNC_PRINT
), "\n PHSV : %#X",stClsEntry
.pstPhsRule
->u8PHSV
);
1384 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, DUMP_INFO
, DBG_LVL_ALL
, "\n********************************************\n");
1393 //-----------------------------------------------------------------------------
1394 // Procedure: phs_decompress
1396 // Description: This routine restores the static fields within the packet.
1399 // in_buf - ptr to incoming packet buffer.
1400 // out_buf - ptr to output buffer where the suppressed header is copied.
1401 // decomp_phs_rules - ptr to PHS rule.
1402 // header_size - ptr to field which holds the phss or phsf_length.
1405 // size -The number of bytes of dynamic fields present with in the incoming packet
1407 // 0 -If PHS rule is NULL.If PHSI is 0 indicateing packet as uncompressed.
1408 //-----------------------------------------------------------------------------
1410 int phs_decompress(unsigned char *in_buf
,unsigned char *out_buf
,
1411 S_PHS_RULE
*decomp_phs_rules
,UINT
*header_size
)
1414 S_PHS_RULE
*tmp_memb
;
1416 unsigned char *phsf
,*phsm
;
1417 int in_buf_len
= *header_size
-1;
1418 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
1420 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_RECEIVE
,DBG_LVL_ALL
,"====>\n");
1423 if((decomp_phs_rules
== NULL
))
1427 tmp_memb
= decomp_phs_rules
;
1428 //BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, PHS_RECEIVE,DBG_LVL_ALL,"\nDECOMP:In phs_decompress PHSI 1 %d",phsi));
1429 //*header_size = tmp_memb->u8PHSFLength;
1430 phss
= tmp_memb
->u8PHSS
;
1431 phsf
= tmp_memb
->u8PHSF
;
1432 phsm
= tmp_memb
->u8PHSM
;
1434 if(phss
> MAX_PHS_LENGTHS
)
1435 phss
= MAX_PHS_LENGTHS
;
1436 //BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, PHS_RECEIVE,DBG_LVL_ALL,"\nDECOMP:In phs_decompress PHSI %d phss %d index %d",phsi,phss,index));
1437 while((phss
> 0) && (size
< in_buf_len
))
1439 bit
= ((*phsm
<< i
)& SUPPRESS
);
1444 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_RECEIVE
,DBG_LVL_ALL
,"\nDECOMP:In phss %d phsf %d ouput %d",
1445 phss
,*phsf
,*out_buf
);
1450 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_RECEIVE
,DBG_LVL_ALL
,"\nDECOMP:In phss %d input %d ouput %d",
1451 phss
,*in_buf
,*out_buf
);
1459 *header_size
=*header_size
+ 1;
1473 //-----------------------------------------------------------------------------
1474 // Procedure: phs_compress
1476 // Description: This routine suppresses the static fields within the packet.Before
1477 // that it will verify the fields to be suppressed with the corresponding fields in the
1478 // phsf. For verification it checks the phsv field of PHS rule. If set and verification
1479 // succeeds it suppresses the field.If any one static field is found different none of
1480 // the static fields are suppressed then the packet is sent as uncompressed packet with
1484 // phs_rule - ptr to PHS rule.
1485 // in_buf - ptr to incoming packet buffer.
1486 // out_buf - ptr to output buffer where the suppressed header is copied.
1487 // header_size - ptr to field which holds the phss.
1490 // size-The number of bytes copied into the output buffer i.e dynamic fields
1491 // 0 -If PHS rule is NULL.If PHSV field is not set.If the verification fails.
1492 //-----------------------------------------------------------------------------
1493 static int phs_compress(S_PHS_RULE
*phs_rule
,unsigned char *in_buf
1494 ,unsigned char *out_buf
,UINT
*header_size
,UINT
*new_header_size
)
1496 unsigned char *old_addr
= out_buf
;
1498 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
1499 if(phs_rule
== NULL
)
1501 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"\nphs_compress(): phs_rule null!");
1502 *out_buf
= ZERO_PHSI
;
1503 return STATUS_PHS_NOCOMPRESSION
;
1507 if(phs_rule
->u8PHSS
<= *new_header_size
)
1509 *header_size
= phs_rule
->u8PHSS
;
1513 *header_size
= *new_header_size
;
1517 supress
= verify_suppress_phsf(in_buf
,out_buf
,phs_rule
->u8PHSF
,
1518 phs_rule
->u8PHSM
, phs_rule
->u8PHSS
, phs_rule
->u8PHSV
,new_header_size
);
1520 if(supress
== STATUS_PHS_COMPRESSED
)
1522 *old_addr
= (unsigned char)phs_rule
->u8PHSI
;
1523 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"\nCOMP:In phs_compress phsi %d",phs_rule
->u8PHSI
);
1527 *old_addr
= ZERO_PHSI
;
1528 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"\nCOMP:In phs_compress PHSV Verification failed");
1534 //-----------------------------------------------------------------------------
1535 // Procedure: verify_suppress_phsf
1537 // Description: This routine verifies the fields of the packet and if all the
1538 // static fields are equal it adds the phsi of that PHS rule.If any static
1539 // field differs it woun't suppress any field.
1542 // rules_set - ptr to classifier_rules.
1543 // in_buffer - ptr to incoming packet buffer.
1544 // out_buffer - ptr to output buffer where the suppressed header is copied.
1545 // phsf - ptr to phsf.
1546 // phsm - ptr to phsm.
1547 // phss - variable holding phss.
1550 // size-The number of bytes copied into the output buffer i.e dynamic fields.
1551 // 0 -Packet has failed the verification.
1552 //-----------------------------------------------------------------------------
1554 static int verify_suppress_phsf(unsigned char *in_buffer
,unsigned char *out_buffer
,
1555 unsigned char *phsf
,unsigned char *phsm
,unsigned int phss
,
1556 unsigned int phsv
,UINT
* new_header_size
)
1558 unsigned int size
=0;
1560 PMINI_ADAPTER Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
1561 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"\nCOMP:In verify_phsf PHSM - 0x%X",*phsm
);
1564 if(phss
>(*new_header_size
))
1566 phss
=*new_header_size
;
1570 bit
= ((*phsm
<< i
)& SUPPRESS
);
1574 if(*in_buffer
!= *phsf
)
1578 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"\nCOMP:In verify_phsf failed for field %d buf %d phsf %d",phss
,*in_buffer
,*phsf
);
1579 return STATUS_PHS_NOCOMPRESSION
;
1583 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"\nCOMP:In verify_phsf success for field %d buf %d phsf %d",phss
,*in_buffer
,*phsf
);
1587 *out_buffer
= *in_buffer
;
1588 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"\nCOMP:In copying_header input %d out %d",*in_buffer
,*out_buffer
);
1602 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, PHS_SEND
, DBG_LVL_ALL
,"\nCOMP:In verify_phsf success");
1603 *new_header_size
= size
;
1604 return STATUS_PHS_COMPRESSED
;