• Home
  • History
  • Annotate
  • Line#
  • Navigate
  • Raw
  • Download
  • only in /asuswrt-rt-n18u-9.0.0.4.380.2695/release/src-rt-6.x.4708/linux/linux-2.6.36/drivers/char/rtl8365mb/
1/*
2 * Copyright (C) 2013 Realtek Semiconductor Corp.
3 * All Rights Reserved.
4 *
5 * This program is the proprietary software of Realtek Semiconductor
6 * Corporation and/or its licensors, and only be used, duplicated,
7 * modified or distributed under the authorized license from Realtek.
8 *
9 * ANY USE OF THE SOFTWARE OTHER THAN AS AUTHORIZED UNDER
10 * THIS LICENSE OR COPYRIGHT LAW IS PROHIBITED.
11 *
12 * $Revision: 51993 $
13 * $Date: 2014-10-08 19:44:38 +0800 (������, 08 ������ 2014) $
14 *
15 * Purpose : RTK switch high-level API for RTL8367/RTL8367C
16 * Feature : Here is a list of all functions and variables in Port module.
17 *
18 */
19
20#include <rtk_switch.h>
21#include <rtk_error.h>
22#include <port.h>
23#ifndef __KERNEL__
24#include <string.h>
25#else
26#include <linux/string.h>
27#endif
28
29#include <rtl8367c_asicdrv.h>
30#include <rtl8367c_asicdrv_port.h>
31#include <rtl8367c_asicdrv_misc.h>
32#include <rtl8367c_asicdrv_portIsolation.h>
33
34static rtk_api_ret_t _rtk_port_FiberModeAbility_set(rtk_port_t port, rtk_port_phy_ability_t *pAbility)
35{
36    rtk_api_ret_t   retVal;
37
38    /* Check Combo port or not */
39    RTK_CHK_PORT_IS_COMBO(port);
40
41    if( (pAbility->Full_1000 == 1) && (pAbility->Full_100 == 1) && (pAbility->AutoNegotiation == 1) )
42    {
43        if ((retVal = rtl8367c_setAsicRegBit(RTL8367C_REG_FIBER_CFG_1, RTL8367C_SDS_FRC_MODE_OFFSET, 0)) != RT_ERR_OK)
44            return retVal;
45
46        if ((retVal = rtl8367c_setAsicRegBits(RTL8367C_REG_FIBER_CFG_1, RTL8367C_SDS_MODE_MASK, 0)) != RT_ERR_OK)
47            return retVal;
48
49        if ((retVal = rtl8367c_setAsicRegBit(RTL8367C_REG_FIB0_CFG00, RTL8367C_FIB0_CFG00_CFG_FIB_ANEN_OFFSET, 1)) != RT_ERR_OK)
50            return retVal;
51    }
52    else if(pAbility->Full_1000 == 1)
53    {
54        if ((retVal = rtl8367c_setAsicRegBit(RTL8367C_REG_FIBER_CFG_1, RTL8367C_SDS_FRC_MODE_OFFSET, 1)) != RT_ERR_OK)
55            return retVal;
56
57        if ((retVal = rtl8367c_setAsicRegBits(RTL8367C_REG_FIBER_CFG_1, RTL8367C_SDS_MODE_MASK, 4)) != RT_ERR_OK)
58            return retVal;
59
60        if ((retVal = rtl8367c_setAsicRegBit(RTL8367C_REG_FIB0_CFG00, RTL8367C_FIB0_CFG00_CFG_FIB_ANEN_OFFSET, 1)) != RT_ERR_OK)
61            return retVal;
62    }
63    else if(pAbility->Full_100 == 1)
64    {
65        if ((retVal = rtl8367c_setAsicRegBit(RTL8367C_REG_FIBER_CFG_1, RTL8367C_SDS_FRC_MODE_OFFSET, 1)) != RT_ERR_OK)
66            return retVal;
67
68        if ((retVal = rtl8367c_setAsicRegBits(RTL8367C_REG_FIBER_CFG_1, RTL8367C_SDS_MODE_MASK, 5)) != RT_ERR_OK)
69            return retVal;
70
71        if ((retVal = rtl8367c_setAsicRegBit(RTL8367C_REG_FIB0_CFG00, RTL8367C_FIB0_CFG00_CFG_FIB_ANEN_OFFSET, 0)) != RT_ERR_OK)
72            return retVal;
73    }
74
75    return RT_ERR_OK;
76}
77
78static rtk_api_ret_t _rtk_port_FiberModeAbility_get(rtk_port_t port, rtk_port_phy_ability_t *pAbility)
79{
80    rtk_api_ret_t   retVal;
81    rtk_uint32      data;
82
83    /* Check Combo port or not */
84    RTK_CHK_PORT_IS_COMBO(port);
85
86    memset(pAbility, 0x00, sizeof(rtk_port_phy_ability_t));
87
88    if ((retVal = rtl8367c_getAsicRegBit(RTL8367C_REG_FIBER_CFG_1, RTL8367C_SDS_FRC_MODE_OFFSET, &data)) != RT_ERR_OK)
89            return retVal;
90
91    if(data == 0)
92    {
93        pAbility->AutoNegotiation = 1;
94        pAbility->Full_1000 = 1;
95        pAbility->Full_100 = 1;
96    }
97    else
98    {
99        if ((retVal = rtl8367c_getAsicRegBits(RTL8367C_REG_FIBER_CFG_1, RTL8367C_SDS_MODE_MASK, &data)) != RT_ERR_OK)
100            return retVal;
101
102        if(data == 4)
103            pAbility->Full_1000 = 1;
104        else if(data == 5)
105            pAbility->Full_100 = 1;
106        else
107            return RT_ERR_FAILED;
108    }
109
110    return RT_ERR_OK;
111}
112
113/* Function Name:
114 *      rtk_port_phyAutoNegoAbility_set
115 * Description:
116 *      Set ethernet PHY auto-negotiation desired ability.
117 * Input:
118 *      port        - port id.
119 *      pAbility    - Ability structure
120 * Output:
121 *      None
122 * Return:
123 *      RT_ERR_OK              	- OK
124 *      RT_ERR_FAILED          	- Failed
125 *      RT_ERR_SMI             	- SMI access error
126 *      RT_ERR_PORT_ID 			- Invalid port number.
127 *      RT_ERR_PHY_REG_ID 		- Invalid PHY address
128 *      RT_ERR_INPUT 			- Invalid input parameters.
129 *      RT_ERR_BUSYWAIT_TIMEOUT - PHY access busy
130 * Note:
131 *      If Full_1000 bit is set to 1, the AutoNegotiation will be automatic set to 1. While both AutoNegotiation and Full_1000 are set to 0, the PHY speed and duplex selection will
132 *      be set as following 100F > 100H > 10F > 10H priority sequence.
133 */
134rtk_api_ret_t rtk_port_phyAutoNegoAbility_set(rtk_port_t port, rtk_port_phy_ability_t *pAbility)
135{
136    rtk_api_ret_t       retVal;
137    rtk_uint32          phyData;
138    rtk_uint32          phyEnMsk0;
139    rtk_uint32          phyEnMsk4;
140    rtk_uint32          phyEnMsk9;
141    rtk_port_media_t    media_type;
142
143    /* Check initialization state */
144    RTK_CHK_INIT_STATE();
145
146    /* Check Port Valid */
147    RTK_CHK_PORT_IS_UTP(port);
148
149    if(NULL == pAbility)
150        return RT_ERR_NULL_POINTER;
151
152    if (pAbility->Half_10 >= RTK_ENABLE_END || pAbility->Full_10 >= RTK_ENABLE_END ||
153       pAbility->Half_100 >= RTK_ENABLE_END || pAbility->Full_100 >= RTK_ENABLE_END ||
154       pAbility->Full_1000 >= RTK_ENABLE_END || pAbility->AutoNegotiation >= RTK_ENABLE_END ||
155       pAbility->AsyFC >= RTK_ENABLE_END || pAbility->FC >= RTK_ENABLE_END)
156        return RT_ERR_INPUT;
157
158    /*for PHY auto mode setup*/
159    pAbility->AutoNegotiation = 1;
160
161    if (rtk_switch_isComboPort(port) == RT_ERR_OK)
162    {
163        if ((retVal = rtk_port_phyComboPortMedia_get(port, &media_type)) != RT_ERR_OK)
164            return retVal;
165
166        if(media_type == PORT_MEDIA_FIBER)
167        {
168            return _rtk_port_FiberModeAbility_set(port, pAbility);
169        }
170    }
171
172    phyEnMsk0 = 0;
173    phyEnMsk4 = 0;
174    phyEnMsk9 = 0;
175
176    if (1 == pAbility->Half_10)
177    {
178        /*10BASE-TX half duplex capable in reg 4.5*/
179        phyEnMsk4 = phyEnMsk4 | (1 << 5);
180
181        /*Speed selection [1:0] */
182        /* 11=Reserved*/
183        /* 10= 1000Mpbs*/
184        /* 01= 100Mpbs*/
185        /* 00= 10Mpbs*/
186        phyEnMsk0 = phyEnMsk0 & (~(1 << 6));
187        phyEnMsk0 = phyEnMsk0 & (~(1 << 13));
188    }
189
190    if (1 == pAbility->Full_10)
191    {
192        /*10BASE-TX full duplex capable in reg 4.6*/
193        phyEnMsk4 = phyEnMsk4 | (1 << 6);
194        /*Speed selection [1:0] */
195        /* 11=Reserved*/
196        /* 10= 1000Mpbs*/
197        /* 01= 100Mpbs*/
198        /* 00= 10Mpbs*/
199        phyEnMsk0 = phyEnMsk0 & (~(1 << 6));
200        phyEnMsk0 = phyEnMsk0 & (~(1 << 13));
201
202        /*Full duplex mode in reg 0.8*/
203        phyEnMsk0 = phyEnMsk0 | (1 << 8);
204
205    }
206
207    if (1 == pAbility->Half_100)
208    {
209        /*100BASE-TX half duplex capable in reg 4.7*/
210        phyEnMsk4 = phyEnMsk4 | (1 << 7);
211        /*Speed selection [1:0] */
212        /* 11=Reserved*/
213        /* 10= 1000Mpbs*/
214        /* 01= 100Mpbs*/
215        /* 00= 10Mpbs*/
216        phyEnMsk0 = phyEnMsk0 & (~(1 << 6));
217        phyEnMsk0 = phyEnMsk0 | (1 << 13);
218    }
219
220
221    if (1 == pAbility->Full_100)
222    {
223        /*100BASE-TX full duplex capable in reg 4.8*/
224        phyEnMsk4 = phyEnMsk4 | (1 << 8);
225        /*Speed selection [1:0] */
226        /* 11=Reserved*/
227        /* 10= 1000Mpbs*/
228        /* 01= 100Mpbs*/
229        /* 00= 10Mpbs*/
230        phyEnMsk0 = phyEnMsk0 & (~(1 << 6));
231        phyEnMsk0 = phyEnMsk0 | (1 << 13);
232        /*Full duplex mode in reg 0.8*/
233        phyEnMsk0 = phyEnMsk0 | (1 << 8);
234    }
235
236
237    if (1 == pAbility->Full_1000)
238    {
239        /*1000 BASE-T FULL duplex capable setting in reg 9.9*/
240        phyEnMsk9 = phyEnMsk9 | (1 << 9);
241
242        /*Speed selection [1:0] */
243        /* 11=Reserved*/
244        /* 10= 1000Mpbs*/
245        /* 01= 100Mpbs*/
246        /* 00= 10Mpbs*/
247        phyEnMsk0 = phyEnMsk0 | (1 << 6);
248        phyEnMsk0 = phyEnMsk0 & (~(1 << 13));
249
250
251        /*Auto-Negotiation setting in reg 0.12*/
252        phyEnMsk0 = phyEnMsk0 | (1 << 12);
253
254     }
255
256    if (1 == pAbility->AutoNegotiation)
257    {
258        /*Auto-Negotiation setting in reg 0.12*/
259        phyEnMsk0 = phyEnMsk0 | (1 << 12);
260    }
261
262    if (1 == pAbility->AsyFC)
263    {
264        /*Asymetric flow control in reg 4.11*/
265        phyEnMsk4 = phyEnMsk4 | (1 << 11);
266    }
267    if (1 == pAbility->FC)
268    {
269        /*Flow control in reg 4.10*/
270        phyEnMsk4 = phyEnMsk4 | (1 << 10);
271    }
272
273    /*1000 BASE-T control register setting*/
274    if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_1000_BASET_CONTROL_REG, &phyData)) != RT_ERR_OK)
275        return retVal;
276
277    phyData = (phyData & (~0x0200)) | phyEnMsk9 ;
278
279    if ((retVal = rtl8367c_setAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_1000_BASET_CONTROL_REG, phyData)) != RT_ERR_OK)
280        return retVal;
281
282    /*Auto-Negotiation control register setting*/
283    if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_AN_ADVERTISEMENT_REG, &phyData)) != RT_ERR_OK)
284        return retVal;
285
286    phyData = (phyData & (~0x0DE0)) | phyEnMsk4;
287    if ((retVal = rtl8367c_setAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_AN_ADVERTISEMENT_REG, phyData)) != RT_ERR_OK)
288        return retVal;
289
290    /*Control register setting and restart auto*/
291    if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_CONTROL_REG, &phyData)) != RT_ERR_OK)
292        return retVal;
293
294    phyData = (phyData & (~0x3140)) | phyEnMsk0;
295    /*If have auto-negotiation capable, then restart auto negotiation*/
296    if (1 == pAbility->AutoNegotiation)
297    {
298        phyData = phyData | (1 << 9);
299    }
300
301    if ((retVal = rtl8367c_setAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_CONTROL_REG, phyData)) != RT_ERR_OK)
302        return retVal;
303
304    return RT_ERR_OK;
305}
306
307/* Function Name:
308 *      rtk_port_phyAutoNegoAbility_get
309 * Description:
310 *      Get PHY ability through PHY registers.
311 * Input:
312 *      port - Port id.
313 * Output:
314 *      pAbility - Ability structure
315 * Return:
316 *      RT_ERR_OK              	- OK
317 *      RT_ERR_FAILED          	- Failed
318 *      RT_ERR_SMI             	- SMI access error
319 *      RT_ERR_PORT_ID 			- Invalid port number.
320 *      RT_ERR_PHY_REG_ID 		- Invalid PHY address
321 *      RT_ERR_INPUT 			- Invalid input parameters.
322 *      RT_ERR_BUSYWAIT_TIMEOUT - PHY access busy
323 * Note:
324 *      Get the capablity of specified PHY.
325 */
326rtk_api_ret_t rtk_port_phyAutoNegoAbility_get(rtk_port_t port, rtk_port_phy_ability_t *pAbility)
327{
328    rtk_api_ret_t       retVal;
329    rtk_uint32          phyData0;
330    rtk_uint32          phyData4;
331    rtk_uint32          phyData9;
332    rtk_port_media_t    media_type;
333
334    /* Check initialization state */
335    RTK_CHK_INIT_STATE();
336
337    /* Check Port Valid */
338    RTK_CHK_PORT_IS_UTP(port);
339
340    if(NULL == pAbility)
341        return RT_ERR_NULL_POINTER;
342
343    if (rtk_switch_isComboPort(port) == RT_ERR_OK)
344    {
345        if ((retVal = rtk_port_phyComboPortMedia_get(port, &media_type)) != RT_ERR_OK)
346            return retVal;
347
348        if(media_type == PORT_MEDIA_FIBER)
349        {
350            return _rtk_port_FiberModeAbility_set(port, pAbility);
351        }
352    }
353
354    /*Control register setting and restart auto*/
355    if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_CONTROL_REG, &phyData0)) != RT_ERR_OK)
356        return retVal;
357
358    /*Auto-Negotiation control register setting*/
359    if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_AN_ADVERTISEMENT_REG, &phyData4)) != RT_ERR_OK)
360        return retVal;
361
362    /*1000 BASE-T control register setting*/
363    if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_1000_BASET_CONTROL_REG, &phyData9)) != RT_ERR_OK)
364        return retVal;
365
366    if (phyData9 & (1 << 9))
367        pAbility->Full_1000 = 1;
368    else
369        pAbility->Full_1000 = 0;
370
371    if (phyData4 & (1 << 11))
372        pAbility->AsyFC = 1;
373    else
374        pAbility->AsyFC = 0;
375
376    if (phyData4 & (1 << 10))
377        pAbility->FC = 1;
378    else
379        pAbility->FC = 0;
380
381
382    if (phyData4 & (1 << 8))
383        pAbility->Full_100 = 1;
384    else
385        pAbility->Full_100 = 0;
386
387    if (phyData4 & (1 << 7))
388        pAbility->Half_100 = 1;
389    else
390        pAbility->Half_100 = 0;
391
392    if (phyData4 & (1 << 6))
393        pAbility->Full_10 = 1;
394    else
395        pAbility->Full_10 = 0;
396
397    if (phyData4 & (1 << 5))
398        pAbility->Half_10 = 1;
399    else
400        pAbility->Half_10 = 0;
401
402
403    if (phyData0 & (1 << 12))
404        pAbility->AutoNegotiation = 1;
405    else
406        pAbility->AutoNegotiation = 0;
407
408    return RT_ERR_OK;
409}
410
411/* Function Name:
412 *      rtk_port_phyForceModeAbility_set
413 * Description:
414 *      Set the port speed/duplex mode/pause/asy_pause in the PHY force mode.
415 * Input:
416 *      port        - port id.
417 *      pAbility    - Ability structure
418 * Output:
419 *      None
420 * Return:
421 *      RT_ERR_OK              	- OK
422 *      RT_ERR_FAILED          	- Failed
423 *      RT_ERR_SMI             	- SMI access error
424 *      RT_ERR_PORT_ID 			- Invalid port number.
425 *      RT_ERR_PHY_REG_ID 		- Invalid PHY address
426 *      RT_ERR_INPUT 			- Invalid input parameters.
427 *      RT_ERR_BUSYWAIT_TIMEOUT - PHY access busy
428 * Note:
429 *      If Full_1000 bit is set to 1, the AutoNegotiation will be automatic set to 1.
430 *      While both AutoNegotiation and Full_1000 are set to 0, the PHY speed and duplex selection will
431 *      be set as following 100F > 100H > 10F > 10H priority sequence.
432 *      This API can be used to configure combo port in fiber mode.
433 *      The possible parameters in fiber mode are Full_1000 and Full 100.
434 *      All the other fields in rtk_port_phy_ability_t will be ignored in fiber port.
435 */
436rtk_api_ret_t rtk_port_phyForceModeAbility_set(rtk_port_t port, rtk_port_phy_ability_t *pAbility)
437{
438     rtk_api_ret_t      retVal;
439     rtk_uint32         phyData;
440     rtk_uint32         phyEnMsk0;
441     rtk_uint32         phyEnMsk4;
442     rtk_uint32         phyEnMsk9;
443     rtk_port_media_t   media_type;
444
445     /* Check initialization state */
446     RTK_CHK_INIT_STATE();
447
448     /* Check Port Valid */
449     RTK_CHK_PORT_IS_UTP(port);
450
451     if(NULL == pAbility)
452        return RT_ERR_NULL_POINTER;
453
454     if (pAbility->Half_10 >= RTK_ENABLE_END || pAbility->Full_10 >= RTK_ENABLE_END ||
455        pAbility->Half_100 >= RTK_ENABLE_END || pAbility->Full_100 >= RTK_ENABLE_END ||
456        pAbility->Full_1000 >= RTK_ENABLE_END || pAbility->AutoNegotiation >= RTK_ENABLE_END ||
457        pAbility->AsyFC >= RTK_ENABLE_END || pAbility->FC >= RTK_ENABLE_END)
458         return RT_ERR_INPUT;
459
460     if (1 == pAbility->Full_1000)
461         return RT_ERR_INPUT;
462
463     if (rtk_switch_isComboPort(port) == RT_ERR_OK)
464     {
465         if ((retVal = rtk_port_phyComboPortMedia_get(port, &media_type)) != RT_ERR_OK)
466             return retVal;
467
468         if(media_type == PORT_MEDIA_FIBER)
469         {
470             return _rtk_port_FiberModeAbility_set(port, pAbility);
471         }
472     }
473
474     /*for PHY force mode setup*/
475     pAbility->AutoNegotiation = 0;
476
477     phyEnMsk0 = 0;
478     phyEnMsk4 = 0;
479     phyEnMsk9 = 0;
480
481     if (1 == pAbility->Half_10)
482     {
483         /*10BASE-TX half duplex capable in reg 4.5*/
484         phyEnMsk4 = phyEnMsk4 | (1 << 5);
485
486         /*Speed selection [1:0] */
487         /* 11=Reserved*/
488         /* 10= 1000Mpbs*/
489         /* 01= 100Mpbs*/
490         /* 00= 10Mpbs*/
491         phyEnMsk0 = phyEnMsk0 & (~(1 << 6));
492         phyEnMsk0 = phyEnMsk0 & (~(1 << 13));
493     }
494
495     if (1 == pAbility->Full_10)
496     {
497         /*10BASE-TX full duplex capable in reg 4.6*/
498         phyEnMsk4 = phyEnMsk4 | (1 << 6);
499         /*Speed selection [1:0] */
500         /* 11=Reserved*/
501         /* 10= 1000Mpbs*/
502         /* 01= 100Mpbs*/
503         /* 00= 10Mpbs*/
504         phyEnMsk0 = phyEnMsk0 & (~(1 << 6));
505         phyEnMsk0 = phyEnMsk0 & (~(1 << 13));
506
507         /*Full duplex mode in reg 0.8*/
508         phyEnMsk0 = phyEnMsk0 | (1 << 8);
509
510     }
511
512     if (1 == pAbility->Half_100)
513     {
514         /*100BASE-TX half duplex capable in reg 4.7*/
515         phyEnMsk4 = phyEnMsk4 | (1 << 7);
516         /*Speed selection [1:0] */
517         /* 11=Reserved*/
518         /* 10= 1000Mpbs*/
519         /* 01= 100Mpbs*/
520         /* 00= 10Mpbs*/
521         phyEnMsk0 = phyEnMsk0 & (~(1 << 6));
522         phyEnMsk0 = phyEnMsk0 | (1 << 13);
523     }
524
525
526     if (1 == pAbility->Full_100)
527     {
528         /*100BASE-TX full duplex capable in reg 4.8*/
529         phyEnMsk4 = phyEnMsk4 | (1 << 8);
530         /*Speed selection [1:0] */
531         /* 11=Reserved*/
532         /* 10= 1000Mpbs*/
533         /* 01= 100Mpbs*/
534         /* 00= 10Mpbs*/
535         phyEnMsk0 = phyEnMsk0 & (~(1 << 6));
536         phyEnMsk0 = phyEnMsk0 | (1 << 13);
537         /*Full duplex mode in reg 0.8*/
538         phyEnMsk0 = phyEnMsk0 | (1 << 8);
539     }
540
541     if (1 == pAbility->AsyFC)
542     {
543         /*Asymetric flow control in reg 4.11*/
544         phyEnMsk4 = phyEnMsk4 | (1 << 11);
545     }
546     if (1 == pAbility->FC)
547     {
548         /*Flow control in reg 4.10*/
549         phyEnMsk4 = phyEnMsk4 | ((1 << 10));
550     }
551
552     /*1000 BASE-T control register setting*/
553     if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_1000_BASET_CONTROL_REG, &phyData)) != RT_ERR_OK)
554         return retVal;
555
556     phyData = (phyData & (~0x0200)) | phyEnMsk9 ;
557
558     if ((retVal = rtl8367c_setAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_1000_BASET_CONTROL_REG, phyData)) != RT_ERR_OK)
559         return retVal;
560
561     /*Auto-Negotiation control register setting*/
562     if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_AN_ADVERTISEMENT_REG, &phyData)) != RT_ERR_OK)
563         return retVal;
564
565     phyData = (phyData & (~0x0DE0)) | phyEnMsk4;
566     if ((retVal = rtl8367c_setAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_AN_ADVERTISEMENT_REG, phyData)) != RT_ERR_OK)
567         return retVal;
568
569     /*Control register setting and power off/on*/
570     phyData = phyEnMsk0 & (~(1 << 12));
571     phyData |= (1 << 11);   /* power down PHY, bit 11 should be set to 1 */
572     if ((retVal = rtl8367c_setAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_CONTROL_REG, phyData)) != RT_ERR_OK)
573         return retVal;
574
575     phyData = phyData & (~(1 << 11));   /* power on PHY, bit 11 should be set to 0*/
576     if ((retVal = rtl8367c_setAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_CONTROL_REG, phyData)) != RT_ERR_OK)
577         return retVal;
578
579     return RT_ERR_OK;
580}
581
582/* Function Name:
583 *      rtk_port_phyForceModeAbility_get
584 * Description:
585 *      Get PHY ability through PHY registers.
586 * Input:
587 *      port - Port id.
588 * Output:
589 *      pAbility - Ability structure
590 * Return:
591 *      RT_ERR_OK              	- OK
592 *      RT_ERR_FAILED          	- Failed
593 *      RT_ERR_SMI             	- SMI access error
594 *      RT_ERR_PORT_ID 			- Invalid port number.
595 *      RT_ERR_PHY_REG_ID 		- Invalid PHY address
596 *      RT_ERR_INPUT 			- Invalid input parameters.
597 *      RT_ERR_BUSYWAIT_TIMEOUT - PHY access busy
598 * Note:
599 *      Get the capablity of specified PHY.
600 */
601rtk_api_ret_t rtk_port_phyForceModeAbility_get(rtk_port_t port, rtk_port_phy_ability_t *pAbility)
602{
603    rtk_api_ret_t       retVal;
604    rtk_uint32          phyData0;
605    rtk_uint32          phyData4;
606    rtk_uint32          phyData9;
607    rtk_port_media_t    media_type;
608
609    /* Check initialization state */
610    RTK_CHK_INIT_STATE();
611
612    /* Check Port Valid */
613     RTK_CHK_PORT_IS_UTP(port);
614
615     if(NULL == pAbility)
616        return RT_ERR_NULL_POINTER;
617
618     if (rtk_switch_isComboPort(port) == RT_ERR_OK)
619     {
620         if ((retVal = rtk_port_phyComboPortMedia_get(port, &media_type)) != RT_ERR_OK)
621             return retVal;
622
623         if(media_type == PORT_MEDIA_FIBER)
624         {
625             return _rtk_port_FiberModeAbility_get(port, pAbility);
626         }
627     }
628
629    /*Control register setting and restart auto*/
630    if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_CONTROL_REG, &phyData0)) != RT_ERR_OK)
631        return retVal;
632
633    /*Auto-Negotiation control register setting*/
634    if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_AN_ADVERTISEMENT_REG, &phyData4)) != RT_ERR_OK)
635        return retVal;
636
637    /*1000 BASE-T control register setting*/
638    if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_1000_BASET_CONTROL_REG, &phyData9)) != RT_ERR_OK)
639        return retVal;
640
641    if (phyData9 & (1 << 9))
642        pAbility->Full_1000 = 1;
643    else
644        pAbility->Full_1000 = 0;
645
646    if (phyData4 & (1 << 11))
647        pAbility->AsyFC = 1;
648    else
649        pAbility->AsyFC = 0;
650
651    if (phyData4 & ((1 << 10)))
652        pAbility->FC = 1;
653    else
654        pAbility->FC = 0;
655
656
657    if (phyData4 & (1 << 8))
658        pAbility->Full_100 = 1;
659    else
660        pAbility->Full_100 = 0;
661
662    if (phyData4 & (1 << 7))
663        pAbility->Half_100 = 1;
664    else
665        pAbility->Half_100 = 0;
666
667    if (phyData4 & (1 << 6))
668        pAbility->Full_10 = 1;
669    else
670        pAbility->Full_10 = 0;
671
672    if (phyData4 & (1 << 5))
673        pAbility->Half_10 = 1;
674    else
675        pAbility->Half_10 = 0;
676
677
678    if (phyData0 & (1 << 12))
679        pAbility->AutoNegotiation = 1;
680    else
681        pAbility->AutoNegotiation = 0;
682
683    return RT_ERR_OK;
684}
685
686/* Function Name:
687 *      rtk_port_phyStatus_get
688 * Description:
689 *      Get ethernet PHY linking status
690 * Input:
691 *      port - Port id.
692 * Output:
693 *      linkStatus  - PHY link status
694 *      speed       - PHY link speed
695 *      duplex      - PHY duplex mode
696 * Return:
697 *      RT_ERR_OK              	- OK
698 *      RT_ERR_FAILED          	- Failed
699 *      RT_ERR_SMI             	- SMI access error
700 *      RT_ERR_PORT_ID 			- Invalid port number.
701 *      RT_ERR_PHY_REG_ID 		- Invalid PHY address
702 *      RT_ERR_INPUT 			- Invalid input parameters.
703 *      RT_ERR_BUSYWAIT_TIMEOUT - PHY access busy
704 * Note:
705 *      API will return auto negotiation status of phy.
706 */
707rtk_api_ret_t rtk_port_phyStatus_get(rtk_port_t port, rtk_port_linkStatus_t *pLinkStatus, rtk_port_speed_t *pSpeed, rtk_port_duplex_t *pDuplex)
708{
709    rtk_api_ret_t retVal;
710    rtk_uint32 phyData;
711
712    /* Check initialization state */
713    RTK_CHK_INIT_STATE();
714
715    /* Check Port Valid */
716    RTK_CHK_PORT_IS_UTP(port);
717
718    if( (NULL == pLinkStatus) || (NULL == pSpeed) || (NULL == pDuplex) )
719        return RT_ERR_NULL_POINTER;
720
721    /*Get PHY resolved register*/
722    if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_RESOLVED_REG, &phyData)) != RT_ERR_OK)
723        return retVal;
724
725    /*check link status*/
726    if (phyData & (1<<2))
727    {
728        *pLinkStatus = 1;
729
730        /*check link speed*/
731        *pSpeed = (phyData&0x0030) >> 4;
732
733        /*check link duplex*/
734        *pDuplex = (phyData&0x0008) >> 3;
735    }
736    else
737    {
738        *pLinkStatus = 0;
739        *pSpeed = 0;
740        *pDuplex = 0;
741    }
742
743    return RT_ERR_OK;
744}
745
746/* Function Name:
747 *      rtk_port_macForceLink_set
748 * Description:
749 *      Set port force linking configuration.
750 * Input:
751 *      port            - port id.
752 *      pPortability    - port ability configuration
753 * Output:
754 *      None
755 * Return:
756 *      RT_ERR_OK           - OK
757 *      RT_ERR_FAILED       - Failed
758 *      RT_ERR_SMI          - SMI access error
759 *      RT_ERR_PORT_ID 		- Invalid port number.
760 * Note:
761 *      This API can set Port/MAC force mode properties.
762 */
763rtk_api_ret_t rtk_port_macForceLink_set(rtk_port_t port, rtk_port_mac_ability_t *pPortability)
764{
765    rtk_api_ret_t retVal;
766    rtl8367c_port_ability_t ability;
767
768    /* Check initialization state */
769    RTK_CHK_INIT_STATE();
770
771    /* Check Port Valid */
772    RTK_CHK_PORT_IS_UTP(port);
773
774    if(NULL == pPortability)
775        return RT_ERR_NULL_POINTER;
776
777    if (pPortability->forcemode >1|| pPortability->speed > 2 || pPortability->duplex > 1 ||
778       pPortability->link > 1 || pPortability->nway > 1 || pPortability->txpause > 1 || pPortability->rxpause > 1)
779        return RT_ERR_INPUT;
780
781    if ((retVal = rtl8367c_getAsicPortForceLink(rtk_switch_port_L2P_get(port), &ability)) != RT_ERR_OK)
782        return retVal;
783
784    ability.forcemode = pPortability->forcemode;
785    ability.speed     = pPortability->speed;
786    ability.duplex    = pPortability->duplex;
787    ability.link      = pPortability->link;
788    ability.nway      = pPortability->nway;
789    ability.txpause   = pPortability->txpause;
790    ability.rxpause   = pPortability->rxpause;
791
792    if ((retVal = rtl8367c_setAsicPortForceLink(rtk_switch_port_L2P_get(port), &ability)) != RT_ERR_OK)
793        return retVal;
794
795    return RT_ERR_OK;
796}
797
798/* Function Name:
799 *      rtk_port_macForceLink_get
800 * Description:
801 *      Get port force linking configuration.
802 * Input:
803 *      port - Port id.
804 * Output:
805 *      pPortability - port ability configuration
806 * Return:
807 *      RT_ERR_OK           - OK
808 *      RT_ERR_FAILED       - Failed
809 *      RT_ERR_SMI          - SMI access error
810 *      RT_ERR_PORT_ID 		- Invalid port number.
811 *      RT_ERR_INPUT 		- Invalid input parameters.
812 * Note:
813 *      This API can get Port/MAC force mode properties.
814 */
815rtk_api_ret_t rtk_port_macForceLink_get(rtk_port_t port, rtk_port_mac_ability_t *pPortability)
816{
817    rtk_api_ret_t retVal;
818    rtl8367c_port_ability_t ability;
819
820    /* Check initialization state */
821    RTK_CHK_INIT_STATE();
822
823    /* Check Port Valid */
824    RTK_CHK_PORT_IS_UTP(port);
825
826    if(NULL == pPortability)
827        return RT_ERR_NULL_POINTER;
828
829    if ((retVal = rtl8367c_getAsicPortForceLink(rtk_switch_port_L2P_get(port), &ability)) != RT_ERR_OK)
830        return retVal;
831
832    pPortability->forcemode = ability.forcemode;
833    pPortability->speed     = ability.speed;
834    pPortability->duplex    = ability.duplex;
835    pPortability->link      = ability.link;
836    pPortability->nway      = ability.nway;
837    pPortability->txpause   = ability.txpause;
838    pPortability->rxpause   = ability.rxpause;
839
840    return RT_ERR_OK;
841}
842
843/* Function Name:
844 *      rtk_port_macForceLinkExt_set
845 * Description:
846 *      Set external interface force linking configuration.
847 * Input:
848 *      port            - external port ID
849 *      mode            - external interface mode
850 *      pPortability    - port ability configuration
851 * Output:
852 *      None
853 * Return:
854 *      RT_ERR_OK           - OK
855 *      RT_ERR_FAILED       - Failed
856 *      RT_ERR_SMI          - SMI access error
857 *      RT_ERR_INPUT 		- Invalid input parameters.
858 * Note:
859 *      This API can set external interface force mode properties.
860 *      The external interface can be set to:
861 *      - MODE_EXT_DISABLE,
862 *      - MODE_EXT_RGMII,
863 *      - MODE_EXT_MII_MAC,
864 *      - MODE_EXT_MII_PHY,
865 *      - MODE_EXT_TMII_MAC,
866 *      - MODE_EXT_TMII_PHY,
867 *      - MODE_EXT_GMII,
868 *      - MODE_EXT_RMII_MAC,
869 *      - MODE_EXT_RMII_PHY,
870 *      - MODE_EXT_SGMII,
871 *      - MODE_EXT_HSGMII
872 */
873rtk_api_ret_t rtk_port_macForceLinkExt_set(rtk_port_t port, rtk_mode_ext_t mode, rtk_port_mac_ability_t *pPortability)
874{
875    rtk_api_ret_t retVal;
876    rtl8367c_port_ability_t ability;
877    rtk_uint32 ext_id;
878
879    /* Check initialization state */
880    RTK_CHK_INIT_STATE();
881
882    /* Check Port Valid */
883    RTK_CHK_PORT_IS_EXT(port);
884
885    if(NULL == pPortability)
886        return RT_ERR_NULL_POINTER;
887
888    if (mode >=MODE_EXT_END)
889        return RT_ERR_INPUT;
890
891    if(mode == MODE_EXT_HSGMII)
892    {
893        if (pPortability->forcemode > 1 || pPortability->speed != PORT_SPEED_2500M || pPortability->duplex != PORT_FULL_DUPLEX ||
894           pPortability->link >= PORT_LINKSTATUS_END || pPortability->nway > 1 || pPortability->txpause > 1 || pPortability->rxpause > 1)
895            return RT_ERR_INPUT;
896
897        if(rtk_switch_isHsgPort(port) != RT_ERR_OK)
898            return RT_ERR_PORT_ID;
899    }
900    else
901    {
902        if (pPortability->forcemode > 1 || pPortability->speed > PORT_SPEED_1000M || pPortability->duplex >= PORT_DUPLEX_END ||
903           pPortability->link >= PORT_LINKSTATUS_END || pPortability->nway > 1 || pPortability->txpause > 1 || pPortability->rxpause > 1)
904            return RT_ERR_INPUT;
905    }
906
907    ext_id = port - 15;
908
909    if(mode == MODE_EXT_DISABLE)
910    {
911        memset(&ability, 0x00, sizeof(rtl8367c_port_ability_t));
912        if ((retVal = rtl8367c_setAsicPortForceLinkExt(ext_id, &ability)) != RT_ERR_OK)
913            return retVal;
914
915        if ((retVal = rtl8367c_setAsicPortExtMode(ext_id, mode)) != RT_ERR_OK)
916            return retVal;
917    }
918    else
919    {
920        if ((retVal = rtl8367c_setAsicPortExtMode(ext_id, mode)) != RT_ERR_OK)
921            return retVal;
922
923        if ((retVal = rtl8367c_getAsicPortForceLinkExt(ext_id, &ability)) != RT_ERR_OK)
924            return retVal;
925
926        ability.forcemode = pPortability->forcemode;
927        ability.speed     = (mode == MODE_EXT_HSGMII) ? PORT_SPEED_1000M : pPortability->speed;
928        ability.duplex    = pPortability->duplex;
929        ability.link      = pPortability->link;
930        ability.nway      = pPortability->nway;
931        ability.txpause   = pPortability->txpause;
932        ability.rxpause   = pPortability->rxpause;
933
934        if ((retVal = rtl8367c_setAsicPortForceLinkExt(ext_id, &ability)) != RT_ERR_OK)
935            return retVal;
936    }
937
938    return RT_ERR_OK;
939}
940
941/* Function Name:
942 *      rtk_port_macForceLinkExt_get
943 * Description:
944 *      Set external interface force linking configuration.
945 * Input:
946 *      port            - external port ID
947 * Output:
948 *      pMode           - external interface mode
949 *      pPortability    - port ability configuration
950 * Return:
951 *      RT_ERR_OK           - OK
952 *      RT_ERR_FAILED       - Failed
953 *      RT_ERR_SMI          - SMI access error
954 *      RT_ERR_INPUT 		- Invalid input parameters.
955 * Note:
956 *      This API can get external interface force mode properties.
957 */
958rtk_api_ret_t rtk_port_macForceLinkExt_get(rtk_port_t port, rtk_mode_ext_t *pMode, rtk_port_mac_ability_t *pPortability)
959{
960    rtk_api_ret_t retVal;
961    rtl8367c_port_ability_t ability;
962    rtk_uint32 ext_id;
963
964    /* Check initialization state */
965    RTK_CHK_INIT_STATE();
966
967    /* Check Port Valid */
968    RTK_CHK_PORT_IS_EXT(port);
969
970    if(NULL == pMode)
971        return RT_ERR_NULL_POINTER;
972
973    if(NULL == pPortability)
974        return RT_ERR_NULL_POINTER;
975
976    ext_id = port - 15;
977
978    if ((retVal = rtl8367c_getAsicPortExtMode(ext_id, (rtk_uint32 *)pMode)) != RT_ERR_OK)
979        return retVal;
980
981    if ((retVal = rtl8367c_getAsicPortForceLinkExt(ext_id, &ability)) != RT_ERR_OK)
982        return retVal;
983
984    pPortability->forcemode = ability.forcemode;
985    pPortability->speed     = (*pMode == MODE_EXT_HSGMII) ? PORT_SPEED_2500M : ability.speed;
986    pPortability->duplex    = ability.duplex;
987    pPortability->link      = ability.link;
988    pPortability->nway      = ability.nway;
989    pPortability->txpause   = ability.txpause;
990    pPortability->rxpause   = ability.rxpause;
991
992    return RT_ERR_OK;
993
994}
995
996/* Function Name:
997 *      rtk_port_macStatus_get
998 * Description:
999 *      Get port link status.
1000 * Input:
1001 *      port - Port id.
1002 * Output:
1003 *      pPortstatus - port ability configuration
1004 * Return:
1005 *      RT_ERR_OK           - OK
1006 *      RT_ERR_FAILED       - Failed
1007 *      RT_ERR_SMI          - SMI access error
1008 *      RT_ERR_PORT_ID 		- Invalid port number.
1009 * Note:
1010 *      This API can get Port/PHY properties.
1011 */
1012rtk_api_ret_t rtk_port_macStatus_get(rtk_port_t port, rtk_port_mac_ability_t *pPortstatus)
1013{
1014    rtk_api_ret_t retVal;
1015    rtl8367c_port_status_t status;
1016    rtk_uint32 hsgsel;
1017
1018    /* Check initialization state */
1019    RTK_CHK_INIT_STATE();
1020
1021    /* Check Port Valid */
1022    RTK_CHK_PORT_VALID(port);
1023
1024    if(NULL == pPortstatus)
1025        return RT_ERR_NULL_POINTER;
1026
1027    if ((retVal = rtl8367c_getAsicPortStatus(rtk_switch_port_L2P_get(port), &status)) != RT_ERR_OK)
1028        return retVal;
1029
1030
1031    pPortstatus->duplex    = status.duplex;
1032    pPortstatus->link      = status.link;
1033    pPortstatus->nway      = status.nway;
1034    pPortstatus->txpause   = status.txpause;
1035    pPortstatus->rxpause   = status.rxpause;
1036
1037    if( (retVal = rtl8367c_getAsicRegBit(RTL8367C_REG_SDS_MISC, RTL8367C_CFG_MAC8_SEL_HSGMII_OFFSET, &hsgsel)) != RT_ERR_OK)
1038            return retVal;
1039
1040    if( (rtk_switch_isHsgPort(port) == RT_ERR_OK) && (hsgsel == 1) )
1041        pPortstatus->speed = PORT_SPEED_2500M;
1042    else
1043        pPortstatus->speed = status.speed;
1044
1045    return RT_ERR_OK;
1046}
1047
1048/* Function Name:
1049 *      rtk_port_macLocalLoopbackEnable_set
1050 * Description:
1051 *      Set Port Local Loopback. (Redirect TX to RX.)
1052 * Input:
1053 *      port    - Port id.
1054 *      enable  - Loopback state, 0:disable, 1:enable
1055 * Output:
1056 *      None.
1057 * Return:
1058 *      RT_ERR_OK           - OK
1059 *      RT_ERR_FAILED       - Failed
1060 *      RT_ERR_SMI          - SMI access error
1061 *      RT_ERR_PORT_ID 		- Invalid port number.
1062 * Note:
1063 *      This API can enable/disable Local loopback in MAC.
1064 *      For UTP port, This API will also enable the digital
1065 *      loopback bit in PHY register for sync of speed between
1066 *      PHY and MAC. For EXT port, users need to force the
1067 *      link state by themself.
1068 */
1069rtk_api_ret_t rtk_port_macLocalLoopbackEnable_set(rtk_port_t port, rtk_enable_t enable)
1070{
1071    rtk_api_ret_t   retVal;
1072    rtk_uint32      data;
1073
1074    /* Check initialization state */
1075    RTK_CHK_INIT_STATE();
1076
1077    /* Check Port Valid */
1078    RTK_CHK_PORT_VALID(port);
1079
1080    if(enable >= RTK_ENABLE_END)
1081        return RT_ERR_INPUT;
1082
1083    if ((retVal = rtl8367c_setAsicPortLoopback(rtk_switch_port_L2P_get(port), enable)) != RT_ERR_OK)
1084        return retVal;
1085
1086    if(rtk_switch_isUtpPort(port) == RT_ERR_OK)
1087    {
1088        if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_CONTROL_REG, &data)) != RT_ERR_OK)
1089            return retVal;
1090
1091        if(enable == ENABLED)
1092            data |= (0x0001 << 14);
1093        else
1094            data &= ~(0x0001 << 14);
1095
1096        if ((retVal = rtl8367c_setAsicPHYReg(rtk_switch_port_L2P_get(port), PHY_CONTROL_REG, data)) != RT_ERR_OK)
1097            return retVal;
1098    }
1099
1100    return RT_ERR_OK;
1101}
1102
1103/* Function Name:
1104 *      rtk_port_macLocalLoopbackEnable_get
1105 * Description:
1106 *      Get Port Local Loopback. (Redirect TX to RX.)
1107 * Input:
1108 *      port    - Port id.
1109 * Output:
1110 *      pEnable  - Loopback state, 0:disable, 1:enable
1111 * Return:
1112 *      RT_ERR_OK           - OK
1113 *      RT_ERR_FAILED       - Failed
1114 *      RT_ERR_SMI          - SMI access error
1115 *      RT_ERR_PORT_ID 		- Invalid port number.
1116 * Note:
1117 *      None.
1118 */
1119rtk_api_ret_t rtk_port_macLocalLoopbackEnable_get(rtk_port_t port, rtk_enable_t *pEnable)
1120{
1121    rtk_api_ret_t retVal;
1122
1123    /* Check initialization state */
1124    RTK_CHK_INIT_STATE();
1125
1126    /* Check Port Valid */
1127    RTK_CHK_PORT_VALID(port);
1128
1129    if(NULL == pEnable)
1130        return RT_ERR_NULL_POINTER;
1131
1132    if ((retVal = rtl8367c_getAsicPortLoopback(rtk_switch_port_L2P_get(port), pEnable)) != RT_ERR_OK)
1133        return retVal;
1134
1135    return RT_ERR_OK;
1136}
1137
1138/* Function Name:
1139 *      rtk_port_phyReg_set
1140 * Description:
1141 *      Set PHY register data of the specific port.
1142 * Input:
1143 *      port    - port id.
1144 *      reg     - Register id
1145 *      regData - Register data
1146 * Output:
1147 *      None
1148 * Return:
1149 *      RT_ERR_OK               - OK
1150 *      RT_ERR_FAILED           - Failed
1151 *      RT_ERR_SMI              - SMI access error
1152 *      RT_ERR_PORT_ID          - Invalid port number.
1153 *      RT_ERR_PHY_REG_ID       - Invalid PHY address
1154 *      RT_ERR_BUSYWAIT_TIMEOUT - PHY access busy
1155 * Note:
1156 *      This API can set PHY register data of the specific port.
1157 */
1158rtk_api_ret_t rtk_port_phyReg_set(rtk_port_t port, rtk_port_phy_reg_t reg, rtk_port_phy_data_t regData)
1159{
1160    rtk_api_ret_t retVal;
1161
1162    /* Check initialization state */
1163    RTK_CHK_INIT_STATE();
1164
1165    /* Check Port Valid */
1166    RTK_CHK_PORT_IS_UTP(port);
1167
1168    if ((retVal = rtl8367c_setAsicPHYReg(rtk_switch_port_L2P_get(port), reg, regData)) != RT_ERR_OK)
1169        return retVal;
1170
1171    return RT_ERR_OK;
1172}
1173
1174/* Function Name:
1175 *      rtk_port_phyReg_get
1176 * Description:
1177 *      Get PHY register data of the specific port.
1178 * Input:
1179 *      port    - Port id.
1180 *      reg     - Register id
1181 * Output:
1182 *      pData   - Register data
1183 * Return:
1184 *      RT_ERR_OK               - OK
1185 *      RT_ERR_FAILED           - Failed
1186 *      RT_ERR_SMI              - SMI access error
1187 *      RT_ERR_PORT_ID          - Invalid port number.
1188 *      RT_ERR_PHY_REG_ID       - Invalid PHY address
1189 *      RT_ERR_BUSYWAIT_TIMEOUT - PHY access busy
1190 * Note:
1191 *      This API can get PHY register data of the specific port.
1192 */
1193rtk_api_ret_t rtk_port_phyReg_get(rtk_port_t port, rtk_port_phy_reg_t reg, rtk_port_phy_data_t *pData)
1194{
1195    rtk_api_ret_t retVal;
1196
1197    /* Check initialization state */
1198    RTK_CHK_INIT_STATE();
1199
1200    /* Check Port Valid */
1201    RTK_CHK_PORT_IS_UTP(port);
1202
1203    if ((retVal = rtl8367c_getAsicPHYReg(rtk_switch_port_L2P_get(port), reg, pData)) != RT_ERR_OK)
1204        return retVal;
1205
1206    return RT_ERR_OK;
1207}
1208
1209/* Function Name:
1210 *      rtk_port_backpressureEnable_set
1211 * Description:
1212 *      Set the half duplex backpressure enable status of the specific port.
1213 * Input:
1214 *      port    - port id.
1215 *      enable  - Back pressure status.
1216 * Output:
1217 *      None
1218 * Return:
1219 *      RT_ERR_OK           - OK
1220 *      RT_ERR_FAILED       - Failed
1221 *      RT_ERR_SMI          - SMI access error
1222 *      RT_ERR_PORT_ID      - Invalid port number.
1223 *      RT_ERR_ENABLE       - Invalid enable input.
1224 * Note:
1225 *      This API can set the half duplex backpressure enable status of the specific port.
1226 *      The half duplex backpressure enable status of the port is as following:
1227 *      - DISABLE(Defer)
1228 *      - ENABLE (Backpressure)
1229 */
1230rtk_api_ret_t rtk_port_backpressureEnable_set(rtk_port_t port, rtk_enable_t enable)
1231{
1232    rtk_api_ret_t retVal;
1233
1234    /* Check initialization state */
1235    RTK_CHK_INIT_STATE();
1236
1237    if (port != RTK_WHOLE_SYSTEM)
1238        return RT_ERR_PORT_ID;
1239
1240    if (enable >= RTK_ENABLE_END)
1241        return RT_ERR_INPUT;
1242
1243    if ((retVal = rtl8367c_setAsicPortJamMode(!enable)) != RT_ERR_OK)
1244        return retVal;
1245
1246    return RT_ERR_OK;
1247}
1248
1249/* Function Name:
1250 *      rtk_port_backpressureEnable_get
1251 * Description:
1252 *      Get the half duplex backpressure enable status of the specific port.
1253 * Input:
1254 *      port - Port id.
1255 * Output:
1256 *      pEnable - Back pressure status.
1257 * Return:
1258 *      RT_ERR_OK           - OK
1259 *      RT_ERR_FAILED       - Failed
1260 *      RT_ERR_SMI          - SMI access error
1261 *      RT_ERR_PORT_ID      - Invalid port number.
1262 * Note:
1263 *      This API can get the half duplex backpressure enable status of the specific port.
1264 *      The half duplex backpressure enable status of the port is as following:
1265 *      - DISABLE(Defer)
1266 *      - ENABLE (Backpressure)
1267 */
1268rtk_api_ret_t rtk_port_backpressureEnable_get(rtk_port_t port, rtk_enable_t *pEnable)
1269{
1270    rtk_api_ret_t retVal;
1271    rtk_uint32 regData;
1272
1273    /* Check initialization state */
1274    RTK_CHK_INIT_STATE();
1275
1276    if (port != RTK_WHOLE_SYSTEM)
1277        return RT_ERR_PORT_ID;
1278
1279    if(NULL == pEnable)
1280        return RT_ERR_NULL_POINTER;
1281
1282    if ((retVal = rtl8367c_getAsicPortJamMode(&regData)) != RT_ERR_OK)
1283        return retVal;
1284
1285    *pEnable = !regData;
1286
1287    return RT_ERR_OK;
1288}
1289
1290/* Function Name:
1291 *      rtk_port_adminEnable_set
1292 * Description:
1293 *      Set port admin configuration of the specific port.
1294 * Input:
1295 *      port    - port id.
1296 *      enable  - Back pressure status.
1297 * Output:
1298 *      None
1299 * Return:
1300 *      RT_ERR_OK           - OK
1301 *      RT_ERR_FAILED       - Failed
1302 *      RT_ERR_SMI          - SMI access error
1303 *      RT_ERR_PORT_ID      - Invalid port number.
1304 *      RT_ERR_ENABLE       - Invalid enable input.
1305 * Note:
1306 *      This API can set port admin configuration of the specific port.
1307 *      The port admin configuration of the port is as following:
1308 *      - DISABLE
1309 *      - ENABLE
1310 */
1311rtk_api_ret_t rtk_port_adminEnable_set(rtk_port_t port, rtk_enable_t enable)
1312{
1313    rtk_api_ret_t retVal;
1314    rtk_uint32      data;
1315
1316    /* Check initialization state */
1317    RTK_CHK_INIT_STATE();
1318
1319    /* Check Port Valid */
1320    RTK_CHK_PORT_IS_UTP(port);
1321
1322    if (enable >= RTK_ENABLE_END)
1323        return RT_ERR_INPUT;
1324
1325    if ((retVal = rtk_port_phyReg_get(port, PHY_CONTROL_REG, &data)) != RT_ERR_OK)
1326        return retVal;
1327
1328    if (ENABLED == enable)
1329    {
1330        data &= 0xF7FF;
1331        data |= 0x0200;
1332    }
1333    else if (DISABLED == enable)
1334    {
1335        data |= 0x0800;
1336    }
1337
1338    if ((retVal = rtk_port_phyReg_set(port, PHY_CONTROL_REG, data)) != RT_ERR_OK)
1339        return retVal;
1340
1341    return RT_ERR_OK;
1342}
1343
1344/* Function Name:
1345 *      rtk_port_adminEnable_get
1346 * Description:
1347 *      Get port admin configurationof the specific port.
1348 * Input:
1349 *      port - Port id.
1350 * Output:
1351 *      pEnable - Back pressure status.
1352 * Return:
1353 *      RT_ERR_OK           - OK
1354 *      RT_ERR_FAILED       - Failed
1355 *      RT_ERR_SMI          - SMI access error
1356 *      RT_ERR_PORT_ID      - Invalid port number.
1357 * Note:
1358 *      This API can get port admin configuration of the specific port.
1359 *      The port admin configuration of the port is as following:
1360 *      - DISABLE
1361 *      - ENABLE
1362 */
1363rtk_api_ret_t rtk_port_adminEnable_get(rtk_port_t port, rtk_enable_t *pEnable)
1364{
1365    rtk_api_ret_t retVal;
1366    rtk_uint32      data;
1367
1368    /* Check initialization state */
1369    RTK_CHK_INIT_STATE();
1370
1371    /* Check Port Valid */
1372    RTK_CHK_PORT_IS_UTP(port);
1373
1374    if(NULL == pEnable)
1375        return RT_ERR_NULL_POINTER;
1376
1377    if ((retVal = rtk_port_phyReg_get(port, PHY_CONTROL_REG, &data)) != RT_ERR_OK)
1378        return retVal;
1379
1380    if ( (data & 0x0800) == 0x0800)
1381    {
1382        *pEnable = DISABLED;
1383    }
1384    else
1385    {
1386        *pEnable = ENABLED;
1387    }
1388
1389    return RT_ERR_OK;
1390}
1391
1392/* Function Name:
1393 *      rtk_port_isolation_set
1394 * Description:
1395 *      Set permitted port isolation portmask
1396 * Input:
1397 *      port         - port id.
1398 *      pPortmask    - Permit port mask
1399 * Output:
1400 *      None
1401 * Return:
1402 *      RT_ERR_OK           - OK
1403 *      RT_ERR_FAILED       - Failed
1404 *      RT_ERR_SMI          - SMI access error
1405 *      RT_ERR_PORT_ID      - Invalid port number.
1406 *      RT_ERR_PORT_MASK    - Invalid portmask.
1407 * Note:
1408 *      This API set the port mask that a port can trasmit packet to of each port
1409 *      A port can only transmit packet to ports included in permitted portmask
1410 */
1411rtk_api_ret_t rtk_port_isolation_set(rtk_port_t port, rtk_portmask_t *pPortmask)
1412{
1413    rtk_api_ret_t retVal;
1414    rtk_uint32 pmask;
1415
1416    /* Check initialization state */
1417    RTK_CHK_INIT_STATE();
1418
1419    /* Check Port Valid */
1420    RTK_CHK_PORT_VALID(port);
1421
1422    if(NULL == pPortmask)
1423        return RT_ERR_NULL_POINTER;
1424
1425    /* check port mask */
1426    RTK_CHK_PORTMASK_VALID(pPortmask);
1427
1428    if ((retVal = rtk_switch_portmask_L2P_get(pPortmask, &pmask)) != RT_ERR_OK)
1429        return retVal;
1430
1431    if ((retVal = rtl8367c_setAsicPortIsolationPermittedPortmask(rtk_switch_port_L2P_get(port), pmask)) != RT_ERR_OK)
1432        return retVal;
1433
1434    return RT_ERR_OK;
1435}
1436
1437/* Function Name:
1438 *      rtk_port_isolation_get
1439 * Description:
1440 *      Get permitted port isolation portmask
1441 * Input:
1442 *      port - Port id.
1443 * Output:
1444 *      pPortmask - Permit port mask
1445 * Return:
1446 *      RT_ERR_OK           - OK
1447 *      RT_ERR_FAILED       - Failed
1448 *      RT_ERR_SMI          - SMI access error
1449 *      RT_ERR_PORT_ID      - Invalid port number.
1450 * Note:
1451 *      This API get the port mask that a port can trasmit packet to of each port
1452 *      A port can only transmit packet to ports included in permitted portmask
1453 */
1454rtk_api_ret_t rtk_port_isolation_get(rtk_port_t port, rtk_portmask_t *pPortmask)
1455{
1456    rtk_api_ret_t retVal;
1457    rtk_uint32 pmask;
1458
1459    /* Check initialization state */
1460    RTK_CHK_INIT_STATE();
1461
1462    /* Check Port Valid */
1463    RTK_CHK_PORT_VALID(port);
1464
1465    if(NULL == pPortmask)
1466        return RT_ERR_NULL_POINTER;
1467
1468    if ((retVal = rtl8367c_getAsicPortIsolationPermittedPortmask(rtk_switch_port_L2P_get(port), &pmask)) != RT_ERR_OK)
1469        return retVal;
1470
1471    if ((retVal = rtk_switch_portmask_P2L_get(pmask, pPortmask)) != RT_ERR_OK)
1472        return retVal;
1473
1474    return RT_ERR_OK;
1475}
1476
1477/* Function Name:
1478 *      rtk_port_rgmiiDelayExt_set
1479 * Description:
1480 *      Set RGMII interface delay value for TX and RX.
1481 * Input:
1482 *      txDelay - TX delay value, 1 for delay 2ns and 0 for no-delay
1483 *      rxDelay - RX delay value, 0~7 for delay setup.
1484 * Output:
1485 *      None
1486 * Return:
1487 *      RT_ERR_OK           - OK
1488 *      RT_ERR_FAILED       - Failed
1489 *      RT_ERR_SMI          - SMI access error
1490 *      RT_ERR_INPUT 		- Invalid input parameters.
1491 * Note:
1492 *      This API can set external interface 2 RGMII delay.
1493 *      In TX delay, there are 2 selection: no-delay and 2ns delay.
1494 *      In RX dekay, there are 8 steps for delay tunning. 0 for no-delay, and 7 for maximum delay.
1495 */
1496rtk_api_ret_t rtk_port_rgmiiDelayExt_set(rtk_port_t port, rtk_data_t txDelay, rtk_data_t rxDelay)
1497{
1498    rtk_api_ret_t retVal;
1499    rtk_uint32 regAddr, regData;
1500
1501    /* Check initialization state */
1502    RTK_CHK_INIT_STATE();
1503
1504    /* Check Port Valid */
1505    RTK_CHK_PORT_IS_EXT(port);
1506
1507    if ((txDelay > 1) || (rxDelay > 7))
1508        return RT_ERR_INPUT;
1509
1510    if(port == EXT_PORT0)
1511        regAddr = RTL8367C_REG_EXT1_RGMXF;
1512    else if(port == EXT_PORT1)
1513        regAddr = RTL8367C_REG_EXT2_RGMXF;
1514    else
1515        return RT_ERR_INPUT;
1516
1517    if ((retVal = rtl8367c_getAsicReg(regAddr, &regData)) != RT_ERR_OK)
1518        return retVal;
1519
1520    regData = (regData & 0xFFF0) | ((txDelay << 3) & 0x0008) | (rxDelay & 0x0007);
1521
1522    if ((retVal = rtl8367c_setAsicReg(regAddr, regData)) != RT_ERR_OK)
1523        return retVal;
1524
1525    return RT_ERR_OK;
1526}
1527
1528/* Function Name:
1529 *      rtk_port_rgmiiDelayExt_get
1530 * Description:
1531 *      Get RGMII interface delay value for TX and RX.
1532 * Input:
1533 *      None
1534 * Output:
1535 *      pTxDelay - TX delay value
1536 *      pRxDelay - RX delay value
1537 * Return:
1538 *      RT_ERR_OK           - OK
1539 *      RT_ERR_FAILED       - Failed
1540 *      RT_ERR_SMI          - SMI access error
1541 *      RT_ERR_INPUT 		- Invalid input parameters.
1542 * Note:
1543 *      This API can set external interface 2 RGMII delay.
1544 *      In TX delay, there are 2 selection: no-delay and 2ns delay.
1545 *      In RX dekay, there are 8 steps for delay tunning. 0 for n0-delay, and 7 for maximum delay.
1546 */
1547rtk_api_ret_t rtk_port_rgmiiDelayExt_get(rtk_port_t port, rtk_data_t *pTxDelay, rtk_data_t *pRxDelay)
1548{
1549    rtk_api_ret_t retVal;
1550    rtk_uint32 regAddr, regData;
1551
1552    /* Check initialization state */
1553    RTK_CHK_INIT_STATE();
1554
1555    /* Check Port Valid */
1556    RTK_CHK_PORT_IS_EXT(port);
1557
1558    if( (NULL == pTxDelay) || (NULL == pRxDelay) )
1559        return RT_ERR_NULL_POINTER;
1560
1561    if(port == EXT_PORT0)
1562        regAddr = RTL8367C_REG_EXT1_RGMXF;
1563    else if(port == EXT_PORT1)
1564        regAddr = RTL8367C_REG_EXT2_RGMXF;
1565    else
1566        return RT_ERR_INPUT;
1567
1568    if ((retVal = rtl8367c_getAsicReg(regAddr, &regData)) != RT_ERR_OK)
1569        return retVal;
1570
1571    *pTxDelay = (regData & 0x0008) >> 3;
1572    *pRxDelay = regData & 0x0007;
1573
1574    return RT_ERR_OK;
1575}
1576
1577/* Function Name:
1578 *      rtk_port_phyEnableAll_set
1579 * Description:
1580 *      Set all PHY enable status.
1581 * Input:
1582 *      enable - PHY Enable State.
1583 * Output:
1584 *      None
1585 * Return:
1586 *      RT_ERR_OK           - OK
1587 *      RT_ERR_FAILED       - Failed
1588 *      RT_ERR_SMI          - SMI access error
1589 *      RT_ERR_ENABLE       - Invalid enable input.
1590 * Note:
1591 *      This API can set all PHY status.
1592 *      The configuration of all PHY is as following:
1593 *      - DISABLE
1594 *      - ENABLE
1595 */
1596rtk_api_ret_t rtk_port_phyEnableAll_set(rtk_enable_t enable)
1597{
1598    rtk_api_ret_t retVal;
1599    rtk_uint32 data;
1600    rtk_uint32 port;
1601
1602    /* Check initialization state */
1603    RTK_CHK_INIT_STATE();
1604
1605    if (enable >= RTK_ENABLE_END)
1606        return RT_ERR_ENABLE;
1607
1608    if ((retVal = rtl8367c_setAsicPortEnableAll(enable)) != RT_ERR_OK)
1609        return retVal;
1610
1611    RTK_SCAN_ALL_LOG_PORT(port)
1612    {
1613        if(rtk_switch_isUtpPort(port) == RT_ERR_OK)
1614        {
1615            if ((retVal = rtk_port_phyReg_get(port, PHY_CONTROL_REG, &data)) != RT_ERR_OK)
1616                return retVal;
1617
1618            if (ENABLED == enable)
1619            {
1620                data &= 0xF7FF;
1621                data |= 0x0200;
1622            }
1623            else
1624            {
1625                data |= 0x0800;
1626            }
1627
1628            if ((retVal = rtk_port_phyReg_set(port, PHY_CONTROL_REG, data)) != RT_ERR_OK)
1629                return retVal;
1630        }
1631    }
1632
1633    return RT_ERR_OK;
1634
1635}
1636
1637/* Function Name:
1638 *      rtk_port_phyEnableAll_get
1639 * Description:
1640 *      Get all PHY enable status.
1641 * Input:
1642 *      None
1643 * Output:
1644 *      pEnable - PHY Enable State.
1645 * Return:
1646 *      RT_ERR_OK           - OK
1647 *      RT_ERR_FAILED       - Failed
1648 *      RT_ERR_SMI          - SMI access error
1649 * Note:
1650 *      This API can set all PHY status.
1651 *      The configuration of all PHY is as following:
1652 *      - DISABLE
1653 *      - ENABLE
1654 */
1655rtk_api_ret_t rtk_port_phyEnableAll_get(rtk_enable_t *pEnable)
1656{
1657    rtk_api_ret_t retVal;
1658
1659    /* Check initialization state */
1660    RTK_CHK_INIT_STATE();
1661
1662    if(NULL == pEnable)
1663        return RT_ERR_NULL_POINTER;
1664
1665    if ((retVal = rtl8367c_getAsicPortEnableAll(pEnable)) != RT_ERR_OK)
1666        return retVal;
1667
1668    return RT_ERR_OK;
1669}
1670
1671/* Function Name:
1672 *      rtk_port_efid_set
1673 * Description:
1674 *      Set port-based enhanced filtering database
1675 * Input:
1676 *      port - Port id.
1677 *      efid - Specified enhanced filtering database.
1678 * Output:
1679 *      None
1680 * Return:
1681 *      RT_ERR_OK              - OK
1682 *      RT_ERR_FAILED          - Failed
1683 *      RT_ERR_SMI             - SMI access error
1684 *      RT_ERR_L2_FID - Invalid fid.
1685 *      RT_ERR_INPUT - Invalid input parameter.
1686 *      RT_ERR_PORT_ID - Invalid port ID.
1687 * Note:
1688 *      The API can set port-based enhanced filtering database.
1689 */
1690rtk_api_ret_t rtk_port_efid_set(rtk_port_t port, rtk_data_t efid)
1691{
1692    rtk_api_ret_t retVal;
1693
1694    /* Check initialization state */
1695    RTK_CHK_INIT_STATE();
1696
1697    /* Check Port Valid */
1698    RTK_CHK_PORT_VALID(port);
1699
1700    /* efid must be 0~7 */
1701    if (efid > RTK_EFID_MAX)
1702        return RT_ERR_INPUT;
1703
1704    if ((retVal = rtl8367c_setAsicPortIsolationEfid(rtk_switch_port_L2P_get(port), efid))!=RT_ERR_OK)
1705        return retVal;
1706
1707    return RT_ERR_OK;
1708}
1709
1710/* Function Name:
1711 *      rtk_port_efid_get
1712 * Description:
1713 *      Get port-based enhanced filtering database
1714 * Input:
1715 *      port - Port id.
1716 * Output:
1717 *      pEfid - Specified enhanced filtering database.
1718 * Return:
1719 *      RT_ERR_OK              - OK
1720 *      RT_ERR_FAILED          - Failed
1721 *      RT_ERR_SMI             - SMI access error
1722 *      RT_ERR_INPUT - Invalid input parameters.
1723 *      RT_ERR_PORT_ID - Invalid port ID.
1724 * Note:
1725 *      The API can get port-based enhanced filtering database status.
1726 */
1727rtk_api_ret_t rtk_port_efid_get(rtk_port_t port, rtk_data_t *pEfid)
1728{
1729    rtk_api_ret_t retVal;
1730
1731    /* Check initialization state */
1732    RTK_CHK_INIT_STATE();
1733
1734    /* Check Port Valid */
1735    RTK_CHK_PORT_VALID(port);
1736
1737    if(NULL == pEfid)
1738        return RT_ERR_NULL_POINTER;
1739
1740    if ((retVal = rtl8367c_getAsicPortIsolationEfid(rtk_switch_port_L2P_get(port), pEfid))!=RT_ERR_OK)
1741        return retVal;
1742
1743    return RT_ERR_OK;
1744}
1745
1746/* Function Name:
1747 *      rtk_port_phyComboPortMedia_set
1748 * Description:
1749 *      Set Combo port media type
1750 * Input:
1751 *      port    - Port id.
1752 *      media   - Media (COPPER or FIBER)
1753 * Output:
1754 *      None.
1755 * Return:
1756 *      RT_ERR_OK               - OK
1757 *      RT_ERR_FAILED           - Failed
1758 *      RT_ERR_SMI              - SMI access error
1759 *      RT_ERR_INPUT            - Invalid input parameters.
1760 *      RT_ERR_PORT_ID          - Invalid port ID.
1761 * Note:
1762 *      The API can Set Combo port media type.
1763 */
1764rtk_api_ret_t rtk_port_phyComboPortMedia_set(rtk_port_t port, rtk_port_media_t media)
1765{
1766    rtk_api_ret_t retVal;
1767
1768    /* Check initialization state */
1769    RTK_CHK_INIT_STATE();
1770
1771    /* Check Port Valid */
1772    RTK_CHK_PORT_IS_UTP(port);
1773
1774    /* Check Combo Port ID */
1775    RTK_CHK_PORT_IS_COMBO(port);
1776
1777    if (media >= PORT_MEDIA_END)
1778        return RT_ERR_INPUT;
1779
1780    if(media == PORT_MEDIA_FIBER)
1781    {
1782        if ((retVal = rtl8367c_setAsicReg(RTL8367C_REG_SDS_INDACS_DATA, 0x8CD3))!=RT_ERR_OK)
1783            return retVal;
1784
1785        if ((retVal = rtl8367c_setAsicReg(RTL8367C_REG_SDS_INDACS_ADR, 0x0426))!=RT_ERR_OK)
1786            return retVal;
1787
1788        if ((retVal = rtl8367c_setAsicReg(RTL8367C_REG_SDS_INDACS_CMD, 0x00C0))!=RT_ERR_OK)
1789            return retVal;
1790
1791        if ((retVal = rtl8367c_setAsicRegBit(RTL8367C_REG_UTP_FIB_DET, RTL8367C_UTP_FIRST_OFFSET, 0))!=RT_ERR_OK)
1792            return retVal;
1793    }
1794    else
1795    {
1796        if ((retVal = rtl8367c_setAsicRegBit(RTL8367C_REG_UTP_FIB_DET, RTL8367C_UTP_FIRST_OFFSET, 1))!=RT_ERR_OK)
1797            return retVal;
1798    }
1799
1800    return RT_ERR_OK;
1801}
1802
1803/* Function Name:
1804 *      rtk_port_phyComboPortMedia_get
1805 * Description:
1806 *      Get Combo port media type
1807 * Input:
1808 *      port    - Port id.
1809 * Output:
1810 *      pMedia  - Media (COPPER or FIBER)
1811 * Return:
1812 *      RT_ERR_OK               - OK
1813 *      RT_ERR_FAILED           - Failed
1814 *      RT_ERR_SMI              - SMI access error
1815 *      RT_ERR_INPUT            - Invalid input parameters.
1816 *      RT_ERR_PORT_ID          - Invalid port ID.
1817 * Note:
1818 *      The API can Set Combo port media type.
1819 */
1820rtk_api_ret_t rtk_port_phyComboPortMedia_get(rtk_port_t port, rtk_port_media_t *pMedia)
1821{
1822    rtk_api_ret_t   retVal;
1823    rtk_uint32      data;
1824
1825    /* Check initialization state */
1826    RTK_CHK_INIT_STATE();
1827
1828    /* Check Port Valid */
1829    RTK_CHK_PORT_IS_UTP(port);
1830
1831    /* Check Combo Port ID */
1832    RTK_CHK_PORT_IS_COMBO(port);
1833
1834    if ((retVal = rtl8367c_getAsicRegBit(RTL8367C_REG_UTP_FIB_DET, RTL8367C_UTP_FIRST_OFFSET, &data))!=RT_ERR_OK)
1835            return retVal;
1836
1837    if(data == 1)
1838        *pMedia = PORT_MEDIA_COPPER;
1839    else
1840        *pMedia = PORT_MEDIA_FIBER;
1841
1842    return RT_ERR_OK;
1843}
1844
1845/* Function Name:
1846 *      rtk_port_rtctEnable_set
1847 * Description:
1848 *      Enable RTCT test
1849 * Input:
1850 *      pPortmask    - Port mask of RTCT enabled port
1851 * Output:
1852 *      None
1853 * Return:
1854 *      RT_ERR_OK               - OK
1855 *      RT_ERR_FAILED           - Failed
1856 *      RT_ERR_SMI              - SMI access error
1857 *      RT_ERR_PORT_MASK        - Invalid port mask.
1858 * Note:
1859 *      The API can enable RTCT Test
1860 */
1861rtk_api_ret_t rtk_port_rtctEnable_set(rtk_portmask_t *pPortmask)
1862{
1863    rtk_api_ret_t   retVal;
1864
1865    /* Check initialization state */
1866    RTK_CHK_INIT_STATE();
1867
1868    /* Check Port Mask Valid */
1869    RTK_CHK_PORTMASK_VALID_ONLY_UTP(pPortmask);
1870
1871    if ((retVal = rtl8367c_setAsicPortRTCT(pPortmask->bits[0]))!=RT_ERR_OK)
1872        return retVal;
1873
1874    return RT_ERR_OK;
1875}
1876
1877/* Function Name:
1878 *      rtk_port_rtctResult_get
1879 * Description:
1880 *      Get the result of RTCT test
1881 * Input:
1882 *      port        - Port ID
1883 * Output:
1884 *      pRtctResult - The result of RTCT result
1885 * Return:
1886 *      RT_ERR_OK                   - OK
1887 *      RT_ERR_FAILED               - Failed
1888 *      RT_ERR_SMI                  - SMI access error
1889 *      RT_ERR_PORT_ID              - Invalid port ID.
1890 *      RT_ERR_PHY_RTCT_NOT_FINISH  - Testing does not finish.
1891 * Note:
1892 *      The API can get RTCT test result.
1893 *      RTCT test may takes 4.8 seconds to finish its test at most.
1894 *      Thus, if this API return RT_ERR_PHY_RTCT_NOT_FINISH or
1895 *      other error code, the result can not be referenced and
1896 *      user should call this API again until this API returns
1897 *      a RT_ERR_OK.
1898 *      The result is stored at pRtctResult->ge_result
1899 *      pRtctResult->linkType is unused.
1900 *      The unit of channel length is 2.5cm. Ex. 300 means 300 * 2.5 = 750cm = 7.5M
1901 */
1902rtk_api_ret_t rtk_port_rtctResult_get(rtk_port_t port, rtk_rtctResult_t *pRtctResult)
1903{
1904    rtk_api_ret_t               retVal;
1905    rtl8367c_port_rtct_result_t result;
1906
1907    /* Check initialization state */
1908    RTK_CHK_INIT_STATE();
1909
1910    /* Check Port Valid */
1911    RTK_CHK_PORT_IS_UTP(port);
1912
1913    memset(pRtctResult, 0x00, sizeof(rtk_rtctResult_t));
1914    if ((retVal = rtl8367c_getAsicPortRTCTResult(port, &result))!=RT_ERR_OK)
1915        return retVal;
1916
1917    pRtctResult->result.ge_result.channelALen = result.channelALen;
1918    pRtctResult->result.ge_result.channelBLen = result.channelBLen;
1919    pRtctResult->result.ge_result.channelCLen = result.channelCLen;
1920    pRtctResult->result.ge_result.channelDLen = result.channelDLen;
1921
1922    pRtctResult->result.ge_result.channelALinedriver = result.channelALinedriver;
1923    pRtctResult->result.ge_result.channelBLinedriver = result.channelBLinedriver;
1924    pRtctResult->result.ge_result.channelCLinedriver = result.channelCLinedriver;
1925    pRtctResult->result.ge_result.channelDLinedriver = result.channelDLinedriver;
1926
1927    pRtctResult->result.ge_result.channelAMismatch = result.channelAMismatch;
1928    pRtctResult->result.ge_result.channelBMismatch = result.channelBMismatch;
1929    pRtctResult->result.ge_result.channelCMismatch = result.channelCMismatch;
1930    pRtctResult->result.ge_result.channelDMismatch = result.channelDMismatch;
1931
1932    pRtctResult->result.ge_result.channelAOpen = result.channelAOpen;
1933    pRtctResult->result.ge_result.channelBOpen = result.channelBOpen;
1934    pRtctResult->result.ge_result.channelCOpen = result.channelCOpen;
1935    pRtctResult->result.ge_result.channelDOpen = result.channelDOpen;
1936
1937    pRtctResult->result.ge_result.channelAShort = result.channelAShort;
1938    pRtctResult->result.ge_result.channelBShort = result.channelBShort;
1939    pRtctResult->result.ge_result.channelCShort = result.channelCShort;
1940    pRtctResult->result.ge_result.channelDShort = result.channelDShort;
1941
1942    return RT_ERR_OK;
1943}
1944