[ragile] support 32c and 4s platform (#8824)
Signed-off-by: pettershao-ragilenetworks pettershao@ragilenetworks.com What I did it Add new platform x86_64-ragile_ra-b6510-32c-r0 (Trident 3) ASIC Vendor: Broadcom Switch ASIC: Trident 3 Port Config: 32x100G Add new platform x86_64-ragile_ra-b6920-4s-r0 (Tomahawk 3) ASIC Vendor: Broadcom Switch ASIC: Tomahawk 3 Port Config: 128x100G -How I did it Provide device and platform related files. -How to verify it show platform fan show platform ssdhealth show platform psustatus show platform summary show platform syseeprom show platform temperature show interface status
This commit is contained in:
parent
5d23035333
commit
0e0772596e
@ -0,0 +1,33 @@
|
||||
# name lanes alias index speed
|
||||
Ethernet1 5,6,7,8 hundredGigE0/1 0 100000
|
||||
Ethernet2 1,2,3,4 hundredGigE0/2 1 100000
|
||||
Ethernet3 13,14,15,16 hundredGigE0/3 2 100000
|
||||
Ethernet4 9,10,11,12 hundredGigE0/4 3 100000
|
||||
Ethernet5 21,22,23,24 hundredGigE0/5 4 100000
|
||||
Ethernet6 17,18,19,20 hundredGigE0/6 5 100000
|
||||
Ethernet7 29,30,31,32 hundredGigE0/7 6 100000
|
||||
Ethernet8 25,26,27,28 hundredGigE0/8 7 100000
|
||||
Ethernet9 37,38,39,40 hundredGigE0/9 8 100000
|
||||
Ethernet10 33,34,35,36 hundredGigE0/10 9 100000
|
||||
Ethernet11 45,46,47,48 hundredGigE0/11 10 100000
|
||||
Ethernet12 41,42,43,44 hundredGigE0/12 11 100000
|
||||
Ethernet13 53,54,55,56 hundredGigE0/13 12 100000
|
||||
Ethernet14 49,50,51,52 hundredGigE0/14 13 100000
|
||||
Ethernet15 61,62,63,64 hundredGigE0/15 14 100000
|
||||
Ethernet16 57,58,59,60 hundredGigE0/16 15 100000
|
||||
Ethernet17 69,70,71,72 hundredGigE0/17 16 100000
|
||||
Ethernet18 65,66,67,68 hundredGigE0/18 17 100000
|
||||
Ethernet19 77,78,79,80 hundredGigE0/19 18 100000
|
||||
Ethernet20 73,74,75,76 hundredGigE0/20 19 100000
|
||||
Ethernet21 85,86,87,88 hundredGigE0/21 20 100000
|
||||
Ethernet22 81,82,83,84 hundredGigE0/22 21 100000
|
||||
Ethernet23 93,94,95,96 hundredGigE0/23 22 100000
|
||||
Ethernet24 89,90,91,92 hundredGigE0/24 23 100000
|
||||
Ethernet25 101,102,103,104 hundredGigE0/25 24 100000
|
||||
Ethernet26 97,98,99,100 hundredGigE0/26 25 100000
|
||||
Ethernet27 109,110,111,112 hundredGigE0/27 26 100000
|
||||
Ethernet28 105,106,107,108 hundredGigE0/28 27 100000
|
||||
Ethernet29 117,118,119,120 hundredGigE0/29 28 100000
|
||||
Ethernet30 113,114,115,116 hundredGigE0/30 29 100000
|
||||
Ethernet31 125,126,127,128 hundredGigE0/31 30 100000
|
||||
Ethernet32 121,122,123,124 hundredGigE0/32 31 100000
|
@ -0,0 +1 @@
|
||||
SAI_INIT_CONFIG_FILE=/usr/share/sonic/hwsku/td3-ra-b6510-32c-32x100G.config.bcm
|
@ -0,0 +1,453 @@
|
||||
cancun_dir=/usr/share/sonic/platform/cancun/sdk_6.5.16/
|
||||
l2_mem_entries=32768
|
||||
l3_mem_entries=16384
|
||||
l3_alpm_enable=2
|
||||
ipv6_lpm_128b_enable=0x1
|
||||
l2xmsg_mode=0
|
||||
l3_max_ecmp_mode=1
|
||||
bcm_num_cos=8
|
||||
bcm_stat_interval=2000000
|
||||
cdma_timeout_usec=3000000
|
||||
core_clock_frequency=1525
|
||||
dpp_clock_ratio=2:3
|
||||
help_cli_enable=1
|
||||
ifp_inports_support_enable=1
|
||||
#lpm_scaling_enable=1
|
||||
max_vp_lags=0
|
||||
mem_cache_enable=0
|
||||
memlist_enable=1
|
||||
miim_intr_enable=0
|
||||
module_64ports=1
|
||||
oversubscribe_mode=1
|
||||
parity_enable=0
|
||||
#pbmp_gport_stack.0=0x0000000000000000000000000000000000000000000000000000000000000000
|
||||
#pbmp_xport_xe.0=0x00000000000000000000000000000000888ffffffffffff9fffffffffffffffe
|
||||
pbmp_xport_xe=0xffffffffffffffffffffffffffffffffffffffffe
|
||||
phy_chain_rx_lane_map_physical{5.0}=0x0123
|
||||
phy_chain_rx_lane_map_physical{1.0}=0x0132
|
||||
phy_chain_rx_lane_map_physical{13.0}=0x0123
|
||||
phy_chain_rx_lane_map_physical{9.0}=0x0132
|
||||
phy_chain_rx_lane_map_physical{21.0}=0x0123
|
||||
phy_chain_rx_lane_map_physical{17.0}=0x0132
|
||||
phy_chain_rx_lane_map_physical{29.0}=0x0123
|
||||
phy_chain_rx_lane_map_physical{25.0}=0x0132
|
||||
phy_chain_rx_lane_map_physical{37.0}=0x0123
|
||||
phy_chain_rx_lane_map_physical{33.0}=0x0132
|
||||
phy_chain_rx_lane_map_physical{45.0}=0x0123
|
||||
phy_chain_rx_lane_map_physical{41.0}=0x0132
|
||||
phy_chain_rx_lane_map_physical{53.0}=0x0123
|
||||
phy_chain_rx_lane_map_physical{49.0}=0x0132
|
||||
phy_chain_rx_lane_map_physical{61.0}=0x0123
|
||||
phy_chain_rx_lane_map_physical{57.0}=0x0132
|
||||
phy_chain_rx_lane_map_physical{69.0}=0x2301
|
||||
phy_chain_rx_lane_map_physical{65.0}=0x2310
|
||||
phy_chain_rx_lane_map_physical{77.0}=0x2301
|
||||
phy_chain_rx_lane_map_physical{73.0}=0x2310
|
||||
phy_chain_rx_lane_map_physical{85.0}=0x2301
|
||||
phy_chain_rx_lane_map_physical{81.0}=0x2310
|
||||
phy_chain_rx_lane_map_physical{93.0}=0x2301
|
||||
phy_chain_rx_lane_map_physical{89.0}=0x2310
|
||||
phy_chain_rx_lane_map_physical{101.0}=0x2301
|
||||
phy_chain_rx_lane_map_physical{97.0}=0x2310
|
||||
phy_chain_rx_lane_map_physical{109.0}=0x2301
|
||||
phy_chain_rx_lane_map_physical{105.0}=0x2310
|
||||
phy_chain_rx_lane_map_physical{117.0}=0x2301
|
||||
phy_chain_rx_lane_map_physical{113.0}=0x2310
|
||||
phy_chain_rx_lane_map_physical{125.0}=0x2301
|
||||
phy_chain_rx_lane_map_physical{121.0}=0x2310
|
||||
|
||||
phy_chain_tx_lane_map_physical{5.0}=0x0123
|
||||
phy_chain_tx_lane_map_physical{1.0}=0x2031
|
||||
phy_chain_tx_lane_map_physical{13.0}=0x0123
|
||||
phy_chain_tx_lane_map_physical{9.0}=0x2031
|
||||
phy_chain_tx_lane_map_physical{21.0}=0x0123
|
||||
phy_chain_tx_lane_map_physical{17.0}=0x2031
|
||||
phy_chain_tx_lane_map_physical{29.0}=0x0123
|
||||
phy_chain_tx_lane_map_physical{25.0}=0x2031
|
||||
phy_chain_tx_lane_map_physical{37.0}=0x0123
|
||||
phy_chain_tx_lane_map_physical{33.0}=0x2031
|
||||
phy_chain_tx_lane_map_physical{45.0}=0x0123
|
||||
phy_chain_tx_lane_map_physical{41.0}=0x2031
|
||||
phy_chain_tx_lane_map_physical{53.0}=0x0123
|
||||
phy_chain_tx_lane_map_physical{49.0}=0x2031
|
||||
phy_chain_tx_lane_map_physical{61.0}=0x0123
|
||||
phy_chain_tx_lane_map_physical{57.0}=0x2031
|
||||
phy_chain_tx_lane_map_physical{69.0}=0x2301
|
||||
phy_chain_tx_lane_map_physical{65.0}=0x0213
|
||||
phy_chain_tx_lane_map_physical{77.0}=0x2301
|
||||
phy_chain_tx_lane_map_physical{73.0}=0x0213
|
||||
phy_chain_tx_lane_map_physical{85.0}=0x2301
|
||||
phy_chain_tx_lane_map_physical{81.0}=0x0213
|
||||
phy_chain_tx_lane_map_physical{93.0}=0x2301
|
||||
phy_chain_tx_lane_map_physical{89.0}=0x0213
|
||||
phy_chain_tx_lane_map_physical{101.0}=0x2301
|
||||
phy_chain_tx_lane_map_physical{97.0}=0x0213
|
||||
phy_chain_tx_lane_map_physical{109.0}=0x2301
|
||||
phy_chain_tx_lane_map_physical{105.0}=0x0213
|
||||
phy_chain_tx_lane_map_physical{117.0}=0x2301
|
||||
phy_chain_tx_lane_map_physical{113.0}=0x0213
|
||||
phy_chain_tx_lane_map_physical{125.0}=0x2301
|
||||
phy_chain_tx_lane_map_physical{121.0}=0x0213
|
||||
|
||||
phy_chain_rx_polarity_flip_physical{5.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{6.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{7.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{8.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{1.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{2.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{3.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{4.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{13.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{14.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{15.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{16.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{9.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{10.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{11.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{12.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{21.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{22.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{23.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{24.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{17.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{18.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{19.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{20.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{29.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{30.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{31.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{32.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{25.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{26.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{27.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{28.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{37.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{38.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{39.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{40.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{33.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{34.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{35.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{36.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{45.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{46.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{47.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{48.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{41.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{42.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{43.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{44.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{53.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{54.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{55.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{56.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{49.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{50.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{51.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{52.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{61.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{62.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{63.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{64.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{57.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{58.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{59.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{60.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{69.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{70.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{71.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{72.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{65.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{66.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{67.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{68.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{77.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{78.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{79.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{80.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{73.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{74.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{75.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{76.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{85.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{86.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{87.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{88.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{81.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{82.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{83.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{84.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{93.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{94.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{95.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{96.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{89.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{90.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{91.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{92.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{101.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{102.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{103.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{104.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{97.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{98.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{99.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{100.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{109.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{110.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{111.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{112.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{105.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{106.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{107.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{108.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{117.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{118.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{119.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{120.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{113.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{114.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{115.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{116.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{125.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{126.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{127.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{128.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{121.0}=0x0
|
||||
phy_chain_rx_polarity_flip_physical{122.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{123.0}=0x1
|
||||
phy_chain_rx_polarity_flip_physical{124.0}=0x1
|
||||
|
||||
phy_chain_tx_polarity_flip_physical{5.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{6.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{7.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{8.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{1.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{2.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{3.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{4.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{13.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{14.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{15.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{16.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{9.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{10.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{11.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{12.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{21.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{22.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{23.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{24.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{17.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{18.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{19.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{20.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{29.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{30.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{31.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{32.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{25.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{26.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{27.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{28.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{37.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{38.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{39.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{40.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{33.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{34.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{35.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{36.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{45.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{46.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{47.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{48.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{41.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{42.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{43.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{44.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{53.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{54.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{55.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{56.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{49.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{50.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{51.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{52.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{61.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{62.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{63.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{64.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{57.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{58.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{59.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{60.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{69.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{70.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{71.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{72.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{65.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{66.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{67.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{68.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{77.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{78.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{79.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{80.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{73.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{74.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{75.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{76.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{85.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{86.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{87.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{88.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{81.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{82.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{83.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{84.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{93.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{94.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{95.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{96.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{89.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{90.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{91.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{92.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{101.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{102.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{103.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{104.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{97.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{98.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{99.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{100.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{109.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{110.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{111.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{112.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{105.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{106.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{107.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{108.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{117.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{118.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{119.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{120.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{113.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{114.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{115.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{116.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{125.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{126.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{127.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{128.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{121.0}=0x1
|
||||
phy_chain_tx_polarity_flip_physical{122.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{123.0}=0x0
|
||||
phy_chain_tx_polarity_flip_physical{124.0}=0x1
|
||||
port_flex_enable=1
|
||||
portmap_5=5:100
|
||||
portmap_1=1:100
|
||||
portmap_13=13:100
|
||||
portmap_9=9:100
|
||||
portmap_21=21:100
|
||||
portmap_17=17:100
|
||||
portmap_29=29:100
|
||||
portmap_25=25:100
|
||||
portmap_37=37:100
|
||||
portmap_33=33:100
|
||||
portmap_45=45:100
|
||||
portmap_41=41:100
|
||||
portmap_53=53:100
|
||||
portmap_49=49:100
|
||||
portmap_61=61:100
|
||||
portmap_57=57:100
|
||||
portmap_71=69:100
|
||||
portmap_67=65:100
|
||||
portmap_79=77:100
|
||||
portmap_75=73:100
|
||||
portmap_87=85:100
|
||||
portmap_83=81:100
|
||||
portmap_95=93:100
|
||||
portmap_91=89:100
|
||||
portmap_103=101:100
|
||||
portmap_99=97:100
|
||||
portmap_111=109:100
|
||||
portmap_107=105:100
|
||||
portmap_119=117:100
|
||||
portmap_115=113:100
|
||||
portmap_127=125:100
|
||||
portmap_123=121:100
|
||||
|
||||
dport_map_port_5=1
|
||||
dport_map_port_1=2
|
||||
dport_map_port_13=3
|
||||
dport_map_port_9=4
|
||||
dport_map_port_21=5
|
||||
dport_map_port_17=6
|
||||
dport_map_port_29=7
|
||||
dport_map_port_25=8
|
||||
dport_map_port_37=9
|
||||
dport_map_port_33=10
|
||||
dport_map_port_45=11
|
||||
dport_map_port_41=12
|
||||
dport_map_port_53=13
|
||||
dport_map_port_49=14
|
||||
dport_map_port_61=15
|
||||
dport_map_port_57=16
|
||||
dport_map_port_71=17
|
||||
dport_map_port_67=18
|
||||
dport_map_port_79=19
|
||||
dport_map_port_75=20
|
||||
dport_map_port_87=21
|
||||
dport_map_port_83=22
|
||||
dport_map_port_95=23
|
||||
dport_map_port_91=24
|
||||
dport_map_port_103=25
|
||||
dport_map_port_99=26
|
||||
dport_map_port_111=27
|
||||
dport_map_port_107=28
|
||||
dport_map_port_119=29
|
||||
dport_map_port_115=30
|
||||
dport_map_port_127=31
|
||||
dport_map_port_123=32
|
||||
|
||||
serdes_if_type_5=14
|
||||
serdes_if_type_1=14
|
||||
serdes_if_type_13=14
|
||||
serdes_if_type_9=14
|
||||
serdes_if_type_21=14
|
||||
serdes_if_type_17=14
|
||||
serdes_if_type_29=14
|
||||
serdes_if_type_25=14
|
||||
serdes_if_type_37=14
|
||||
serdes_if_type_33=14
|
||||
serdes_if_type_45=14
|
||||
serdes_if_type_41=14
|
||||
serdes_if_type_53=14
|
||||
serdes_if_type_49=14
|
||||
serdes_if_type_61=14
|
||||
serdes_if_type_57=14
|
||||
serdes_if_type_71=14
|
||||
serdes_if_type_67=14
|
||||
serdes_if_type_79=14
|
||||
serdes_if_type_75=14
|
||||
serdes_if_type_87=14
|
||||
serdes_if_type_83=14
|
||||
serdes_if_type_95=14
|
||||
serdes_if_type_91=14
|
||||
serdes_if_type_103=14
|
||||
serdes_if_type_99=14
|
||||
serdes_if_type_111=14
|
||||
serdes_if_type_107=14
|
||||
serdes_if_type_119=14
|
||||
serdes_if_type_115=14
|
||||
serdes_if_type_127=14
|
||||
serdes_if_type_123=14
|
||||
|
||||
reglist_enable=1
|
||||
scache_filename=/tmp/scache
|
||||
schan_intr_enable=0
|
||||
stable_size=0x5500000
|
||||
tdma_timeout_usec=3000000
|
1
device/ragile/x86_64-ragile_ra-b6510-32c-r0/bcm.rc
Normal file
1
device/ragile/x86_64-ragile_ra-b6510-32c-r0/bcm.rc
Normal file
@ -0,0 +1 @@
|
||||
rcload /usr/share/sonic/platform/led_proc_init.soc
|
1
device/ragile/x86_64-ragile_ra-b6510-32c-r0/bcm_pre.rc
Normal file
1
device/ragile/x86_64-ragile_ra-b6510-32c-r0/bcm_pre.rc
Normal file
@ -0,0 +1 @@
|
||||
m0 load 0 0 /usr/share/sonic/platform/linkscan_led.bin
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
BIN
device/ragile/x86_64-ragile_ra-b6510-32c-r0/custom_led.bin
Normal file
BIN
device/ragile/x86_64-ragile_ra-b6510-32c-r0/custom_led.bin
Normal file
Binary file not shown.
1
device/ragile/x86_64-ragile_ra-b6510-32c-r0/default_sku
Normal file
1
device/ragile/x86_64-ragile_ra-b6510-32c-r0/default_sku
Normal file
@ -0,0 +1 @@
|
||||
RA-B6510-32C t1
|
136
device/ragile/x86_64-ragile_ra-b6510-32c-r0/dev.xml
Normal file
136
device/ragile/x86_64-ragile_ra-b6510-32c-r0/dev.xml
Normal file
@ -0,0 +1,136 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!--
|
||||
### type 1 result/1000
|
||||
type 2 result/100
|
||||
type 3 read bit
|
||||
### property need check must add int front
|
||||
-->
|
||||
<catalog>
|
||||
<fans>
|
||||
<fan id="fan1" >
|
||||
<property name="present" location="2-000d/fan_present" type="3" bit="0" decode="fanpresent" default="0"/>
|
||||
<property name="status" location="2-000d/fan_status" type="3" bit="0" decode="fanstatus" default="1"/>
|
||||
<property name="fru" e2type="fru" location="16-0050/eeprom"/>
|
||||
<!--property name="hw_version" location="/sys/bus/i2c/devices/16-0050/fan_hw_version" type="0" bit="0"/>
|
||||
<property name="fan_type" location="/sys/bus/i2c/devices/16-0050/fan_type"/>
|
||||
<property name="sn" location="/sys/bus/i2c/devices/16-0050/fan_sn"/-->
|
||||
<property name="Speed" location="2-000d/fan1_1_real_speed"/>
|
||||
</fan>
|
||||
<fan id="fan2" >
|
||||
<property name="present" location="2-000d/fan_present" type="3" bit="1" decode="fanpresent" default="0" />
|
||||
<property name="status" location="2-000d/fan_status" type="3" bit="1" decode="fanstatus" default="1"/>
|
||||
<property name="fru" e2type="fru" location="17-0050/eeprom"/>
|
||||
<!--property name="hw_version" location="4-0053/fan_hw_version" type="0" bit="0"/>
|
||||
<property name="fan_type" location="4-0053/fan_type"/>
|
||||
<property name="sn" location="4-0053/fan_sn"/-->
|
||||
<property name="Speed" location="2-000d/fan2_1_real_speed"/>
|
||||
</fan>
|
||||
<fan id="fan3" >
|
||||
<property name="present" location="2-000d/fan_present" type="3" bit="2" decode="fanpresent" default="0"/>
|
||||
<property name="status" location="2-000d/fan_status" type="3" bit="2" decode="fanstatus" default="1"/>
|
||||
<property name="fru" e2type="fru" location="18-0050/eeprom"/>
|
||||
<!--property name="hw_version" location="5-0053/fan_hw_version" type="0" bit="0"/>
|
||||
<property name="fan_type" location="5-0053/fan_type"/>
|
||||
<property name="sn" location="5-0053/fan_sn"/-->
|
||||
<property name="Speed" location="2-000d/fan3_1_real_speed"/>
|
||||
</fan>
|
||||
<fan id="fan4" >
|
||||
<property name="present" location="2-000d/fan_present" type="3" bit="3" decode="fanpresent" default="0"/>
|
||||
<property name="status" location="2-000d/fan_status" type="3" bit="3" decode="fanstatus" default="1"/>
|
||||
<property name="fru" e2type="fru" location="19-0050/eeprom"/>
|
||||
<!--property name="hw_version" location="6-0053/fan_hw_version" type="0" bit="0"/>
|
||||
<property name="fan_type" location="6-0053/fan_type"/>
|
||||
<property name="sn" location="6-0053/fan_sn"/-->
|
||||
<property name="Speed" location="2-000d/fan4_1_real_speed"/>
|
||||
</fan>
|
||||
<fan id="fan5" >
|
||||
<property name="present" location="2-000d/fan_present" type="3" bit="4" decode="fanpresent" default="0"/>
|
||||
<property name="status" location="2-000d/fan_status" type="3" bit="4" decode="fanstatus" default="1"/>
|
||||
<property name="fru" e2type="fru" location="20-0050/eeprom"/>
|
||||
<!--property name="hw_version" location="6-0053/fan_hw_version" type="0" bit="0"/>
|
||||
<property name="fan_type" location="6-0053/fan_type"/>
|
||||
<property name="sn" location="6-0053/fan_sn"/-->
|
||||
<property name="Speed" location="2-000d/fan5_1_real_speed"/>
|
||||
</fan>
|
||||
</fans>
|
||||
<temps>
|
||||
<temp id="air_inlet" >
|
||||
<property name="temp1_input" location="/3-0048/hwmon/*/temp1_input" type="1"/>
|
||||
<property name="temp1_max" location="/3-0048/hwmon/*/temp1_max" type="1" />
|
||||
<property name="temp1_max_hyst" location="/3-0048/hwmon/*/temp1_max_hyst" type="1" />
|
||||
</temp>
|
||||
<temp id="air_outlet" >
|
||||
<property name="temp1_input" location="/3-0049/hwmon/*/temp1_input" type="1" />
|
||||
<property name="temp1_max" location="/3-0049/hwmon/*/temp1_max" type="1" />
|
||||
<property name="temp1_max_hyst" location="/3-0049/hwmon/*/temp1_max_hyst" type="1" />
|
||||
</temp>
|
||||
<temp id="air_hotlet" >
|
||||
<property name="temp1_input" location="/3-004a/hwmon/*/temp1_input" type="1"/>
|
||||
<property name="temp1_max" location="/3-004a/hwmon/*/temp1_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/3-004a/hwmon/*/temp1_max_hyst" type="1"/>
|
||||
</temp>
|
||||
</temps>
|
||||
<psus>
|
||||
<psu id="psu1" >
|
||||
<property name="present" location="6-000d/psu_status" type="3" bit="0" decode="psucheck" default="0"/>
|
||||
<property name="status" location="6-000d/psu_status" type="3" bit="1" decode="psustatus" default="1"/>
|
||||
<property name="sn" location="24-0050/psu_sn" />
|
||||
<property name="in_current" location="24-0058/hwmon/*/curr1_input" type="1" />
|
||||
<property name="in_voltage" location="24-0058/hwmon/*/in1_input" type="1"/>
|
||||
<property name="out_voltage" location="24-0058/hwmon/*/in2_input" type="1" />
|
||||
<property name="out_current" location="24-0058/hwmon/*/curr2_input" type="1" />
|
||||
<property name="temp" location="24-0058/hwmon/*/temp1_input" type="1"/>
|
||||
<property name="hw" location="24-0050/psu_hw" />
|
||||
<property name="type1" location="24-0050/psu_type" decode="psutype"/>
|
||||
<property name="fan_speed" location="24-0058/hwmon/*/fan1_input" />
|
||||
<property name="in_power" location="24-0058/hwmon/*/power1_input" type="5"/>
|
||||
<property name="out_power" location="24-0058/hwmon/*/power2_input" type="5"/>
|
||||
</psu>
|
||||
<psu id="psu2" >
|
||||
<property name="present" location="6-000d/psu_status" type="3" bit="4" decode="psucheck" default="0"/>
|
||||
<property name="status" location="6-000d/psu_status" type="3" bit="5" decode="psustatus" default="1"/>
|
||||
<property name="sn" location="25-0050/psu_sn" />
|
||||
<property name="in_current" location="25-0058/hwmon/*/curr1_input" type="1" />
|
||||
<property name="in_voltage" location="25-0058/hwmon/*/in1_input" type="1"/>
|
||||
<property name="out_voltage" location="25-0058/hwmon/*/in2_input" type="1" />
|
||||
<property name="out_current" location="25-0058/hwmon/*/curr2_input" type="1" />
|
||||
<property name="temp" location="25-0058/hwmon/*/temp1_input" type="1"/>
|
||||
<property name="hw" location="25-0050/psu_hw" />
|
||||
<property name="type1" location="25-0050/psu_type" decode="psutype"/>
|
||||
<property name="fan_speed" location="25-0058/hwmon/*/fan1_input" />
|
||||
<property name="in_power" location="25-0058/hwmon/*/power1_input" type="5"/>
|
||||
<property name="out_power" location="25-0058/hwmon/*/power2_input" type="5"/>
|
||||
</psu>
|
||||
</psus>
|
||||
<cpus location="/sys/class/hwmon/hwmon0"/>
|
||||
<ports_rx>
|
||||
<mgmt_rx id="mgmt" sender="eth0" >
|
||||
<property name="mgmt" location="/eth0/statistics/rx_packets" type="4"/>
|
||||
</mgmt_rx>
|
||||
</ports_rx>
|
||||
<decode>
|
||||
<fanpresent>
|
||||
<code key="1" value="ABSENT"/>
|
||||
<code key="0" value="PRESENT"/>
|
||||
</fanpresent>
|
||||
<fanstatus>
|
||||
<code key="1" value="OK"/>
|
||||
<code key="0" value="NOT OK"/>
|
||||
</fanstatus>
|
||||
<psucheck>
|
||||
<code key="1" value="ABSENT"/>
|
||||
<code key="0" value="PRESENT"/>
|
||||
</psucheck>
|
||||
<psustatus>
|
||||
<code key="1" value="OK"/>
|
||||
<code key="0" value="NOT OK"/>
|
||||
</psustatus>
|
||||
|
||||
<psutype>
|
||||
<code key="CSU550AP-3-300" value="RG-PA550I-F"/>
|
||||
<code key="DPS-550AB-39 A" value="RG-PA550I-F"/>
|
||||
<code key="CSU550AP-3-501" value="RG-PA550I-F"/>
|
||||
</psutype>
|
||||
</decode>
|
||||
</catalog>
|
||||
|
217
device/ragile/x86_64-ragile_ra-b6510-32c-r0/fantlv.py
Normal file
217
device/ragile/x86_64-ragile_ra-b6510-32c-r0/fantlv.py
Normal file
@ -0,0 +1,217 @@
|
||||
#!/usr/bin/python
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
class FantlvException(Exception):
|
||||
def __init__(self, message='fantlverror', code=-100):
|
||||
err = 'errcode: {0} message:{1}'.format(code, message)
|
||||
Exception.__init__(self, err)
|
||||
self.code = code
|
||||
self.message = message
|
||||
|
||||
class fan_tlv(object):
|
||||
HEAD_INFO = "\x01\x7e\x01\xf1"
|
||||
VERSION = 0x01
|
||||
FLAG = 0x7E
|
||||
HW_VER = 0X01
|
||||
TYPE = 0xf1
|
||||
TLV_LEN = 00
|
||||
_FAN_TLV_HDR_LEN = 6
|
||||
_FAN_TLV_CRC_LEN = 2
|
||||
|
||||
_FAN_TLV_TYPE_NAME = 0x02
|
||||
_FAN_TLV_TYPE_SN = 0x03
|
||||
_FAN_TLV_TYPE_HW_INFO = 0x05
|
||||
_FAN_TLV_TYPE_DEV_TYPE = 0x06
|
||||
|
||||
_fandecodetime = 0
|
||||
|
||||
@property
|
||||
def dstatus(self):
|
||||
return self._dstatus
|
||||
|
||||
@property
|
||||
def typename(self):
|
||||
return self._typename
|
||||
|
||||
@property
|
||||
def typesn(self):
|
||||
return self._typesn
|
||||
|
||||
@property
|
||||
def typehwinfo(self):
|
||||
return self._typehwinfo
|
||||
|
||||
@property
|
||||
def typedevtype(self):
|
||||
return self._typedevtype
|
||||
|
||||
@property
|
||||
def fanbus(self):
|
||||
return self._fanbus
|
||||
|
||||
@property
|
||||
def fanloc(self):
|
||||
return self._fanloc
|
||||
|
||||
@property
|
||||
def fandecodetime(self):
|
||||
return self._fandecodetime
|
||||
|
||||
def __init__(self):
|
||||
self._typename = ""
|
||||
self._typesn = ""
|
||||
self._typehwinfo = ""
|
||||
self._typedevtype = ""
|
||||
self._dstatus = 0
|
||||
|
||||
def strtoarr(self, string):
|
||||
s = []
|
||||
if not isinstance(string, str):
|
||||
return s
|
||||
for index in string:
|
||||
s.append(index)
|
||||
return s
|
||||
|
||||
def str_to_hex(self,rest_v):
|
||||
value = 0
|
||||
for index in range(len(rest_v)):
|
||||
value |= ord(rest_v[index]) << ((len(rest_v) - index - 1) * 8)
|
||||
return value
|
||||
|
||||
def hex_to_str(self,s):
|
||||
len_t = len(s)
|
||||
if len_t % 2 != 0:
|
||||
return 0
|
||||
ret = ""
|
||||
for t in range(0, int(len_t / 2)):
|
||||
ret += chr(int(s[2 * t:2 * t + 2], 16))
|
||||
return ret
|
||||
|
||||
def generate_fan_value(self):
|
||||
bin_buffer = [chr(0xff)] * 256
|
||||
bin_buffer[0] = chr(self.VERSION)
|
||||
bin_buffer[1] = chr(self.FLAG)
|
||||
bin_buffer[2] = chr(self.HW_VER)
|
||||
bin_buffer[3] = chr(self.TYPE)
|
||||
|
||||
temp_t = "%08x" % self.typedevtype
|
||||
typedevtype_t = self.hex_to_str(temp_t)
|
||||
total_len = len(self.typename) + len(self.typesn) + \
|
||||
len(self.typehwinfo) + len(typedevtype_t) + 8
|
||||
|
||||
bin_buffer[4] = chr(total_len >> 8)
|
||||
bin_buffer[5] = chr(total_len & 0x00FF)
|
||||
|
||||
index_start = 6
|
||||
bin_buffer[index_start] = chr(self._FAN_TLV_TYPE_NAME)
|
||||
bin_buffer[index_start + 1] = chr(len(self.typename))
|
||||
bin_buffer[index_start + 2: index_start + 2 +
|
||||
len(self.typename)] = self.strtoarr(self.typename)
|
||||
index_start = index_start + 2 + len(self.typename)
|
||||
|
||||
bin_buffer[index_start] = chr(self._FAN_TLV_TYPE_SN)
|
||||
bin_buffer[index_start + 1] = chr(len(self.typesn))
|
||||
bin_buffer[index_start + 2:index_start + 2 +
|
||||
len(self.typesn)] = self.strtoarr(self.typesn)
|
||||
index_start = index_start + 2 + len(self.typesn)
|
||||
|
||||
bin_buffer[index_start] = chr(self._FAN_TLV_TYPE_HW_INFO)
|
||||
bin_buffer[index_start + 1] = chr(len(self.typehwinfo))
|
||||
bin_buffer[index_start + 2:index_start + 2 +
|
||||
len(self.typehwinfo)] = self.strtoarr(self.typehwinfo)
|
||||
index_start = index_start + 2 + len(self.typehwinfo)
|
||||
|
||||
bin_buffer[index_start] = chr(self._FAN_TLV_TYPE_DEV_TYPE)
|
||||
bin_buffer[index_start + 1] = chr(len(typedevtype_t))
|
||||
bin_buffer[index_start + 2:index_start + 2 +
|
||||
len(typedevtype_t)] = self.strtoarr(typedevtype_t)
|
||||
index_start = index_start + 2 + len(typedevtype_t)
|
||||
|
||||
crcs = fan_tlv.fancrc(''.join(bin_buffer[0:index_start]))
|
||||
bin_buffer[index_start] = chr(crcs >> 8)
|
||||
bin_buffer[index_start + 1] = chr(crcs & 0x00ff)
|
||||
# printvalue(bin_buffer)
|
||||
return bin_buffer
|
||||
|
||||
def encode(self):
|
||||
pass
|
||||
|
||||
def decode(self, e2):
|
||||
if e2[0:4] != self.HEAD_INFO:
|
||||
raise FantlvException("Fan tlv head info error,not fan tlv type", -10)
|
||||
ret = []
|
||||
self.VERSION = ord(e2[0])
|
||||
self.FLAG = ord(e2[1])
|
||||
self.HW_VER = ord(e2[2])
|
||||
self.TYPE = ord(e2[3])
|
||||
self.TLV_LEN = (ord(e2[4]) << 8) | ord(e2[5])
|
||||
|
||||
tlv_index = self._FAN_TLV_HDR_LEN
|
||||
tlv_end = self._FAN_TLV_HDR_LEN + self.TLV_LEN
|
||||
|
||||
if len(e2) < self._FAN_TLV_HDR_LEN + self.TLV_LEN + 2:
|
||||
raise FantlvException("Fan tlv eeprom len error!", -2)
|
||||
sumcrc = fan_tlv.fancrc(e2[0:self._FAN_TLV_HDR_LEN + self.TLV_LEN])
|
||||
readcrc = ord(e2[self._FAN_TLV_HDR_LEN + self.TLV_LEN]
|
||||
) << 8 | ord(e2[self._FAN_TLV_HDR_LEN + self.TLV_LEN + 1])
|
||||
if sumcrc != readcrc:
|
||||
raise FantlvException("Fan tlv eeprom checksum error!", -1)
|
||||
else:
|
||||
self._dstatus = 0
|
||||
while (tlv_index + 2) < len(e2) and tlv_index < tlv_end:
|
||||
s = self.decoder(
|
||||
e2[tlv_index:tlv_index + 2 + ord(e2[tlv_index + 1])])
|
||||
tlv_index += ord(e2[tlv_index + 1]) + 2
|
||||
ret.append(s)
|
||||
# sumcrc = fan_tlv.fancrc(e2[0:self._FAN_TLV_HDR_LEN + self.TLV_LEN])
|
||||
|
||||
return ret
|
||||
|
||||
@staticmethod
|
||||
def fancrc(t):
|
||||
sum = 0
|
||||
for index in range(len(t)):
|
||||
sum += ord(t[index])
|
||||
return sum
|
||||
|
||||
def decoder(self, t):
|
||||
try:
|
||||
name = ""
|
||||
value = ""
|
||||
if ord(t[0]) == self._FAN_TLV_TYPE_NAME:
|
||||
name = "Product Name"
|
||||
_len = ord(t[1])
|
||||
value = t[2:2 + ord(t[1])]
|
||||
self._typename = value
|
||||
elif ord(t[0]) == self._FAN_TLV_TYPE_SN:
|
||||
name = "serial Number"
|
||||
_len = ord(t[1])
|
||||
value = t[2:2 + ord(t[1])]
|
||||
self._typesn = value
|
||||
elif ord(t[0]) == self._FAN_TLV_TYPE_HW_INFO:
|
||||
name = "hardware info"
|
||||
_len = ord(t[1])
|
||||
value = t[2:2 + ord(t[1])]
|
||||
self._typehwinfo = value
|
||||
elif ord(t[0]) == self._FAN_TLV_TYPE_DEV_TYPE:
|
||||
name = "dev type"
|
||||
_len = ord(t[1])
|
||||
value = "0x"
|
||||
for c in t[2:2 + ord(t[1])]:
|
||||
value += "%02X" % (ord(c),)
|
||||
self._typedevtype = int(value,16)
|
||||
except Exception as e:
|
||||
print e
|
||||
return {"name": name, "code": ord(t[0]), "value": value,"lens": _len}
|
||||
|
||||
def __str__(self):
|
||||
formatstr = "VERSION : 0x%02x \n" \
|
||||
" FLAG : 0x%02x \n" \
|
||||
" HW_VER : 0x%02x \n" \
|
||||
" TYPE : 0x%02x \n" \
|
||||
"typename : %s \n" \
|
||||
"typesn : %s \n" \
|
||||
"typehwinfo : %s \n"
|
||||
return formatstr % (self.VERSION, self.FLAG, self.HW_VER, self.TYPE, self.typename, self.typesn, self.typehwinfo)
|
||||
|
||||
|
950
device/ragile/x86_64-ragile_ra-b6510-32c-r0/fru.py
Normal file
950
device/ragile/x86_64-ragile_ra-b6510-32c-r0/fru.py
Normal file
@ -0,0 +1,950 @@
|
||||
#!/usr/bin/python
|
||||
# -*- coding: utf-8 -*-
|
||||
import collections
|
||||
from bitarray import bitarray
|
||||
from datetime import datetime, timedelta
|
||||
import sys
|
||||
|
||||
__DEBUG__ = "N"
|
||||
|
||||
|
||||
class FruException(Exception):
|
||||
def __init__(self, message='fruerror', code=-100):
|
||||
err = 'errcode: {0} message:{1}'.format(code, message)
|
||||
Exception.__init__(self, err)
|
||||
self.code = code
|
||||
self.message = message
|
||||
|
||||
|
||||
def e_print(err):
|
||||
print("ERROR: " + err)
|
||||
|
||||
|
||||
def d_print(debug_info):
|
||||
if(__DEBUG__ == "Y"):
|
||||
print(debug_info)
|
||||
|
||||
|
||||
class FruUtil():
|
||||
@staticmethod
|
||||
def decodeLength(value):
|
||||
a = bitarray(8)
|
||||
a.setall(True)
|
||||
a[0:1] = 0
|
||||
a[1:2] = 0
|
||||
x = ord(a.tobytes())
|
||||
return x & ord(value)
|
||||
|
||||
@staticmethod
|
||||
def minToData():
|
||||
starttime = datetime(1996, 1, 1, 0, 0, 0)
|
||||
endtime = datetime.now()
|
||||
seconds = (endtime - starttime).total_seconds()
|
||||
mins = seconds / 60
|
||||
m = int(round(mins))
|
||||
return m
|
||||
|
||||
@staticmethod
|
||||
def getTimeFormat():
|
||||
return datetime.now().strftime('%Y-%m-%d')
|
||||
|
||||
@staticmethod
|
||||
def getTypeLength(value):
|
||||
if value is None:
|
||||
return 0
|
||||
a = bitarray(8)
|
||||
a.setall(False)
|
||||
a[0:1] = 1
|
||||
a[1:2] = 1
|
||||
x = ord(a.tobytes())
|
||||
return x | len(value)
|
||||
|
||||
@staticmethod
|
||||
def checksum(b):
|
||||
result = 0
|
||||
for i in range(len(b)):
|
||||
result += ord(b[i])
|
||||
return (0x100 - (result & 0xff)) & 0xff
|
||||
|
||||
|
||||
class BaseArea(object):
|
||||
SUGGESTED_SIZE_COMMON_HEADER = 8
|
||||
SUGGESTED_SIZE_INTERNAL_USE_AREA = 72
|
||||
SUGGESTED_SIZE_CHASSIS_INFO_AREA = 32
|
||||
SUGGESTED_SIZE_BOARD_INFO_AREA = 80
|
||||
SUGGESTED_SIZE_PRODUCT_INFO_AREA = 80
|
||||
|
||||
INITVALUE = b'\x00'
|
||||
resultvalue = INITVALUE * 256
|
||||
COMMON_HEAD_VERSION = b'\x01'
|
||||
__childList = None
|
||||
|
||||
def __init__(self, name="", size=0, offset=0):
|
||||
self.__childList = []
|
||||
self._offset = offset
|
||||
self.name = name
|
||||
self._size = size
|
||||
self._isPresent = False
|
||||
self._data = b'\x00' * size
|
||||
self.__dataoffset = 0
|
||||
|
||||
@property
|
||||
def childList(self):
|
||||
return self.__childList
|
||||
|
||||
@childList.setter
|
||||
def childList(self, value):
|
||||
self.__childList = value
|
||||
|
||||
@property
|
||||
def offset(self):
|
||||
return self._offset
|
||||
|
||||
@offset.setter
|
||||
def offset(self, value):
|
||||
self._offset = value
|
||||
|
||||
@property
|
||||
def size(self):
|
||||
return self._size
|
||||
|
||||
@size.setter
|
||||
def size(self, value):
|
||||
self._size = value
|
||||
|
||||
@property
|
||||
def data(self):
|
||||
return self._data
|
||||
|
||||
@data.setter
|
||||
def data(self, value):
|
||||
self._data = value
|
||||
|
||||
@property
|
||||
def isPresent(self):
|
||||
return self._isPresent
|
||||
|
||||
@isPresent.setter
|
||||
def isPresent(self, value):
|
||||
self._isPresent = value
|
||||
|
||||
|
||||
class InternalUseArea(BaseArea):
|
||||
pass
|
||||
|
||||
|
||||
class ChassisInfoArea(BaseArea):
|
||||
pass
|
||||
|
||||
|
||||
class BoardInfoArea(BaseArea):
|
||||
_boardTime = None
|
||||
_fields = None
|
||||
_mfg_date = None
|
||||
|
||||
def __str__(self):
|
||||
formatstr = "version : %x\n" \
|
||||
"length : %d \n" \
|
||||
"language : %x \n" \
|
||||
"mfg_date : %s \n" \
|
||||
"boardManufacturer : %s \n" \
|
||||
"boardProductName : %s \n" \
|
||||
"boardSerialNumber : %s \n" \
|
||||
"boardPartNumber : %s \n" \
|
||||
"fruFileId : %s \n"
|
||||
|
||||
tmpstr = formatstr % (ord(self.boardversion), self.size,
|
||||
self.language, self.getMfgRealData(),
|
||||
self.boardManufacturer, self.boardProductName,
|
||||
self.boardSerialNumber, self.boardPartNumber,
|
||||
self.fruFileId)
|
||||
for i in range(1, 11):
|
||||
valtmp = "boardextra%d" % i
|
||||
if hasattr(self, valtmp):
|
||||
valtmpval = getattr(self, valtmp)
|
||||
tmpstr += "boardextra%d : %s \n" % (i, valtmpval)
|
||||
else:
|
||||
break
|
||||
|
||||
return tmpstr
|
||||
|
||||
def todict(self):
|
||||
dic = collections.OrderedDict()
|
||||
dic["boardversion"] = ord(self.boardversion)
|
||||
dic["boardlength"] = self.size
|
||||
dic["boardlanguage"] = self.language
|
||||
dic["boardmfg_date"] = self.getMfgRealData()
|
||||
dic["boardManufacturer"] = self.boardManufacturer
|
||||
dic["boardProductName"] = self.boardProductName
|
||||
dic["boardSerialNumber"] = self.boardSerialNumber
|
||||
dic["boardPartNumber"] = self.boardPartNumber
|
||||
dic["boardfruFileId"] = self.fruFileId
|
||||
for i in range(1, 11):
|
||||
valtmp = "boardextra%d" % i
|
||||
if hasattr(self, valtmp):
|
||||
valtmpval = getattr(self, valtmp)
|
||||
dic[valtmp] = valtmpval
|
||||
else:
|
||||
break
|
||||
return dic
|
||||
|
||||
def decodedata(self):
|
||||
index = 0
|
||||
self.areaversion = self.data[index]
|
||||
index += 1
|
||||
d_print("decode length :%d class size:%d" %
|
||||
((ord(self.data[index]) * 8), self.size))
|
||||
index += 2
|
||||
|
||||
timetmp = self.data[index: index + 3]
|
||||
self.mfg_date = ord(timetmp[0]) | (
|
||||
ord(timetmp[1]) << 8) | (ord(timetmp[2]) << 16)
|
||||
d_print("decode getMfgRealData :%s" % self.getMfgRealData())
|
||||
index += 3
|
||||
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
self.boardManufacturer = self.data[index + 1: index + templen + 1]
|
||||
index += templen + 1
|
||||
d_print("decode boardManufacturer:%s" % self.boardManufacturer)
|
||||
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
self.boardProductName = self.data[index + 1: index + templen + 1]
|
||||
index += templen + 1
|
||||
d_print("decode boardProductName:%s" % self.boardProductName)
|
||||
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
self.boardSerialNumber = self.data[index + 1: index + templen + 1]
|
||||
index += templen + 1
|
||||
d_print("decode boardSerialNumber:%s" % self.boardSerialNumber)
|
||||
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
self.boardPartNumber = self.data[index + 1: index + templen + 1]
|
||||
index += templen + 1
|
||||
d_print("decode boardPartNumber:%s" % self.boardPartNumber)
|
||||
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
self.fruFileId = self.data[index + 1: index + templen + 1]
|
||||
index += templen + 1
|
||||
d_print("decode fruFileId:%s" % self.fruFileId)
|
||||
|
||||
|
||||
for i in range(1, 11):
|
||||
valtmp = "boardextra%d" % i
|
||||
if self.data[index] != chr(0xc1):
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
tmpval = self.data[index + 1: index + templen + 1]
|
||||
setattr(self, valtmp, tmpval)
|
||||
index += templen + 1
|
||||
d_print("decode boardextra%d:%s" % (i, tmpval))
|
||||
else:
|
||||
break
|
||||
|
||||
def recalcute(self):
|
||||
d_print("boardInfoArea version:%x" % ord(self.boardversion))
|
||||
d_print("boardInfoArea length:%d" % self.size)
|
||||
d_print("boardInfoArea language:%x" % self.language)
|
||||
self.mfg_date = FruUtil.minToData()
|
||||
d_print("boardInfoArea mfg_date:%x" % self.mfg_date)
|
||||
|
||||
self.data = chr(ord(self.boardversion)) + \
|
||||
chr(self.size / 8) + chr(self.language)
|
||||
|
||||
self.data += chr(self.mfg_date & 0xFF)
|
||||
self.data += chr((self.mfg_date >> 8) & 0xFF)
|
||||
self.data += chr((self.mfg_date >> 16) & 0xFF)
|
||||
|
||||
d_print("boardInfoArea boardManufacturer:%s" % self.boardManufacturer)
|
||||
typelength = FruUtil.getTypeLength(self.boardManufacturer)
|
||||
self.data += chr(typelength)
|
||||
self.data += self.boardManufacturer
|
||||
|
||||
d_print("boardInfoArea boardProductName:%s" % self.boardProductName)
|
||||
self.data += chr(FruUtil.getTypeLength(self.boardProductName))
|
||||
self.data += self.boardProductName
|
||||
|
||||
d_print("boardInfoArea boardSerialNumber:%s" % self.boardSerialNumber)
|
||||
self.data += chr(FruUtil.getTypeLength(self.boardSerialNumber))
|
||||
self.data += self.boardSerialNumber
|
||||
|
||||
d_print("boardInfoArea boardPartNumber:%s" % self.boardPartNumber)
|
||||
self.data += chr(FruUtil.getTypeLength(self.boardPartNumber))
|
||||
self.data += self.boardPartNumber
|
||||
|
||||
d_print("boardInfoArea fruFileId:%s" % self.fruFileId)
|
||||
self.data += chr(FruUtil.getTypeLength(self.fruFileId))
|
||||
self.data += self.fruFileId
|
||||
|
||||
for i in range(1, 11):
|
||||
valtmp = "boardextra%d" % i
|
||||
if hasattr(self, valtmp):
|
||||
valtmpval = getattr(self, valtmp)
|
||||
d_print("boardInfoArea boardextra%d:%s" % (i, valtmpval))
|
||||
self.data += chr(FruUtil.getTypeLength(valtmpval))
|
||||
if valtmpval is None:
|
||||
pass
|
||||
else:
|
||||
self.data += valtmpval
|
||||
else:
|
||||
break
|
||||
|
||||
self.data += chr(0xc1)
|
||||
|
||||
if len(self.data) > (self.size - 1):
|
||||
incr = (len(self.data) - self.size) / 8 + 1
|
||||
self.size += incr * 8
|
||||
|
||||
self.data = self.data[0:1] + chr(self.size / 8) + self.data[2:]
|
||||
d_print("self data:%d" % len(self.data))
|
||||
d_print("self size:%d" % self.size)
|
||||
d_print("adjust size:%d" % (self.size - len(self.data) - 1))
|
||||
self.data = self.data.ljust((self.size - 1), self.INITVALUE)
|
||||
|
||||
# checksum
|
||||
checksum = FruUtil.checksum(self.data)
|
||||
d_print("board info checksum:%x" % checksum)
|
||||
self.data += chr(checksum)
|
||||
|
||||
def getMfgRealData(self):
|
||||
starttime = datetime(1996, 1, 1, 0, 0, 0)
|
||||
mactime = starttime + timedelta(minutes=self.mfg_date)
|
||||
return mactime
|
||||
|
||||
@property
|
||||
def language(self):
|
||||
self._language = 25
|
||||
return self._language
|
||||
|
||||
@property
|
||||
def mfg_date(self):
|
||||
return self._mfg_date
|
||||
|
||||
@mfg_date.setter
|
||||
def mfg_date(self, val):
|
||||
self._mfg_date = val
|
||||
|
||||
@property
|
||||
def boardversion(self):
|
||||
self._boardversion = self.COMMON_HEAD_VERSION
|
||||
return self._boardversion
|
||||
|
||||
@property
|
||||
def fruFileId(self):
|
||||
return self._FRUFileID
|
||||
|
||||
@fruFileId.setter
|
||||
def fruFileId(self, val):
|
||||
self._FRUFileID = val
|
||||
|
||||
@property
|
||||
def boardPartNumber(self):
|
||||
return self._boardPartNumber
|
||||
|
||||
@boardPartNumber.setter
|
||||
def boardPartNumber(self, val):
|
||||
self._boardPartNumber = val
|
||||
|
||||
@property
|
||||
def boardSerialNumber(self):
|
||||
return self._boardSerialNumber
|
||||
|
||||
@boardSerialNumber.setter
|
||||
def boardSerialNumber(self, val):
|
||||
self._boardSerialNumber = val
|
||||
|
||||
@property
|
||||
def boardProductName(self):
|
||||
return self._boradProductName
|
||||
|
||||
@boardProductName.setter
|
||||
def boardProductName(self, val):
|
||||
self._boradProductName = val
|
||||
|
||||
@property
|
||||
def boardManufacturer(self):
|
||||
return self._boardManufacturer
|
||||
|
||||
@boardManufacturer.setter
|
||||
def boardManufacturer(self, val):
|
||||
self._boardManufacturer = val
|
||||
|
||||
@property
|
||||
def boardTime(self):
|
||||
return self._boardTime
|
||||
|
||||
@boardTime.setter
|
||||
def boardTime(self, val):
|
||||
self._boardTime = val
|
||||
|
||||
@property
|
||||
def fields(self):
|
||||
return self._fields
|
||||
|
||||
@fields.setter
|
||||
def fields(self, val):
|
||||
self._fields = val
|
||||
|
||||
|
||||
class ProductInfoArea(BaseArea):
|
||||
_productManufacturer = None
|
||||
_productAssetTag = None
|
||||
_FRUFileID = None
|
||||
|
||||
def __str__(self):
|
||||
formatstr = "version : %x\n" \
|
||||
"length : %d \n" \
|
||||
"language : %x \n" \
|
||||
"productManufacturer : %s \n" \
|
||||
"productName : %s \n" \
|
||||
"productPartModelName: %s \n" \
|
||||
"productVersion : %s \n" \
|
||||
"productSerialNumber : %s \n" \
|
||||
"productAssetTag : %s \n" \
|
||||
"fruFileId : %s \n"
|
||||
|
||||
tmpstr = formatstr % (ord(self.areaversion), self.size,
|
||||
self.language, self.productManufacturer,
|
||||
self.productName, self.productPartModelName,
|
||||
self.productVersion, self.productSerialNumber,
|
||||
self.productAssetTag, self.fruFileId)
|
||||
|
||||
for i in range(1, 11):
|
||||
valtmp = "productextra%d" % i
|
||||
if hasattr(self, valtmp):
|
||||
valtmpval = getattr(self, valtmp)
|
||||
tmpstr += "productextra%d : %s \n" % (i, valtmpval)
|
||||
else:
|
||||
break
|
||||
|
||||
return tmpstr
|
||||
|
||||
def todict(self):
|
||||
dic = collections.OrderedDict()
|
||||
dic["productversion"] = ord(self.areaversion)
|
||||
dic["productlength"] = self.size
|
||||
dic["productlanguage"] = self.language
|
||||
dic["productManufacturer"] = self.productManufacturer
|
||||
dic["productName"] = self.productName
|
||||
dic["productPartModelName"] = self.productPartModelName
|
||||
dic["productVersion"] = int(self.productVersion, 16)
|
||||
dic["productSerialNumber"] = self.productSerialNumber
|
||||
dic["productAssetTag"] = self.productAssetTag
|
||||
dic["productfruFileId"] = self.fruFileId
|
||||
for i in range(1, 11):
|
||||
valtmp = "productextra%d" % i
|
||||
if hasattr(self, valtmp):
|
||||
valtmpval = getattr(self, valtmp)
|
||||
dic[valtmp] = valtmpval
|
||||
else:
|
||||
break
|
||||
return dic
|
||||
|
||||
def decodedata(self):
|
||||
index = 0
|
||||
self.areaversion = self.data[index] # 0
|
||||
index += 1
|
||||
d_print("decode length %d" % (ord(self.data[index]) * 8))
|
||||
d_print("class size %d" % self.size)
|
||||
index += 2
|
||||
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
self.productManufacturer = self.data[index + 1: index + templen + 1]
|
||||
index += templen + 1
|
||||
d_print("decode productManufacturer:%s" % self.productManufacturer)
|
||||
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
self.productName = self.data[index + 1: index + templen + 1]
|
||||
index += templen + 1
|
||||
d_print("decode productName:%s" % self.productName)
|
||||
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
self.productPartModelName = self.data[index + 1: index + templen + 1]
|
||||
index += templen + 1
|
||||
d_print("decode productPartModelName:%s" % self.productPartModelName)
|
||||
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
self.productVersion = self.data[index + 1: index + templen + 1]
|
||||
index += templen + 1
|
||||
d_print("decode productVersion:%s" % self.productVersion)
|
||||
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
self.productSerialNumber = self.data[index + 1: index + templen + 1]
|
||||
index += templen + 1
|
||||
d_print("decode productSerialNumber:%s" % self.productSerialNumber)
|
||||
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
self.productAssetTag = self.data[index + 1: index + templen + 1]
|
||||
index += templen + 1
|
||||
d_print("decode productAssetTag:%s" % self.productAssetTag)
|
||||
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
self.fruFileId = self.data[index + 1: index + templen + 1]
|
||||
index += templen + 1
|
||||
d_print("decode fruFileId:%s" % self.fruFileId)
|
||||
|
||||
for i in range(1, 11):
|
||||
valtmp = "productextra%d" % i
|
||||
if self.data[index] != chr(0xc1) and index < self.size - 1:
|
||||
templen = FruUtil.decodeLength(self.data[index])
|
||||
if templen == 0:
|
||||
break
|
||||
tmpval = self.data[index + 1: index + templen + 1]
|
||||
d_print("decode boardextra%d:%s" % (i, tmpval))
|
||||
setattr(self, valtmp, tmpval)
|
||||
index += templen + 1
|
||||
else:
|
||||
break
|
||||
|
||||
@property
|
||||
def productVersion(self):
|
||||
return self._productVersion
|
||||
|
||||
@productVersion.setter
|
||||
def productVersion(self, name):
|
||||
self._productVersion = name
|
||||
|
||||
@property
|
||||
def areaversion(self):
|
||||
self._areaversion = self.COMMON_HEAD_VERSION
|
||||
return self._areaversion
|
||||
|
||||
@areaversion.setter
|
||||
def areaversion(self, name):
|
||||
self._areaversion = name
|
||||
|
||||
@property
|
||||
def language(self):
|
||||
self._language = 25
|
||||
return self._language
|
||||
|
||||
@property
|
||||
def productManufacturer(self):
|
||||
return self._productManufacturer
|
||||
|
||||
@productManufacturer.setter
|
||||
def productManufacturer(self, name):
|
||||
self._productManufacturer = name
|
||||
|
||||
@property
|
||||
def productName(self):
|
||||
return self._productName
|
||||
|
||||
@productName.setter
|
||||
def productName(self, name):
|
||||
self._productName = name
|
||||
|
||||
@property
|
||||
def productPartModelName(self):
|
||||
return self._productPartModelName
|
||||
|
||||
@productPartModelName.setter
|
||||
def productPartModelName(self, name):
|
||||
self._productPartModelName = name
|
||||
|
||||
@property
|
||||
def productSerialNumber(self):
|
||||
return self._productSerialNumber
|
||||
|
||||
@productSerialNumber.setter
|
||||
def productSerialNumber(self, name):
|
||||
self._productSerialNumber = name
|
||||
|
||||
@property
|
||||
def productAssetTag(self):
|
||||
return self._productAssetTag
|
||||
|
||||
@productAssetTag.setter
|
||||
def productAssetTag(self, name):
|
||||
self._productAssetTag = name
|
||||
|
||||
@property
|
||||
def fruFileId(self):
|
||||
return self._FRUFileID
|
||||
|
||||
@fruFileId.setter
|
||||
def fruFileId(self, name):
|
||||
self._FRUFileID = name
|
||||
|
||||
def recalcute(self):
|
||||
d_print("product version:%x" % ord(self.areaversion))
|
||||
d_print("product length:%d" % self.size)
|
||||
d_print("product language:%x" % self.language)
|
||||
self.data = chr(ord(self.areaversion)) + \
|
||||
chr(self.size / 8) + chr(self.language)
|
||||
|
||||
typelength = FruUtil.getTypeLength(self.productManufacturer)
|
||||
self.data += chr(typelength)
|
||||
self.data += self.productManufacturer
|
||||
|
||||
self.data += chr(FruUtil.getTypeLength(self.productName))
|
||||
self.data += self.productName
|
||||
|
||||
self.data += chr(FruUtil.getTypeLength(self.productPartModelName))
|
||||
self.data += self.productPartModelName
|
||||
|
||||
self.data += chr(FruUtil.getTypeLength(self.productVersion))
|
||||
self.data += self.productVersion
|
||||
|
||||
self.data += chr(FruUtil.getTypeLength(self.productSerialNumber))
|
||||
self.data += self.productSerialNumber
|
||||
|
||||
self.data += chr(FruUtil.getTypeLength(self.productAssetTag))
|
||||
if self.productAssetTag is not None:
|
||||
self.data += self.productAssetTag
|
||||
|
||||
self.data += chr(FruUtil.getTypeLength(self.fruFileId))
|
||||
self.data += self.fruFileId
|
||||
|
||||
for i in range(1, 11):
|
||||
valtmp = "productextra%d" % i
|
||||
if hasattr(self, valtmp):
|
||||
valtmpval = getattr(self, valtmp)
|
||||
d_print("boardInfoArea productextra%d:%s" % (i, valtmpval))
|
||||
self.data += chr(FruUtil.getTypeLength(valtmpval))
|
||||
if valtmpval is None:
|
||||
pass
|
||||
else:
|
||||
self.data += valtmpval
|
||||
else:
|
||||
break
|
||||
|
||||
self.data += chr(0xc1)
|
||||
if len(self.data) > (self.size - 1):
|
||||
incr = (len(self.data) - self.size) / 8 + 1
|
||||
self.size += incr * 8
|
||||
d_print("self.data:%d" % len(self.data))
|
||||
d_print("self.size:%d" % self.size)
|
||||
|
||||
self.data = self.data[0:1] + chr(self.size / 8) + self.data[2:]
|
||||
self.data = self.data.ljust((self.size - 1), self.INITVALUE)
|
||||
checksum = FruUtil.checksum(self.data)
|
||||
d_print("board info checksum:%x" % checksum)
|
||||
self.data += chr(checksum)
|
||||
|
||||
|
||||
class MultiRecordArea(BaseArea):
|
||||
pass
|
||||
|
||||
|
||||
class Field(object):
|
||||
|
||||
def __init__(self, fieldType="ASCII", fieldData=""):
|
||||
self.fieldData = fieldData
|
||||
self.fieldType = fieldType
|
||||
|
||||
@property
|
||||
def data(self):
|
||||
return self._data
|
||||
|
||||
@property
|
||||
def fieldType(self):
|
||||
return self._fieldType
|
||||
|
||||
@property
|
||||
def fieldData(self):
|
||||
return self._fieldData
|
||||
|
||||
|
||||
class ipmifru(BaseArea):
|
||||
_BoardInfoArea = None
|
||||
_ProductInfoArea = None
|
||||
_InternalUseArea = None
|
||||
_ChassisInfoArea = None
|
||||
_multiRecordArea = None
|
||||
_productinfoAreaOffset = BaseArea.INITVALUE
|
||||
_boardInfoAreaOffset = BaseArea.INITVALUE
|
||||
_internalUserAreaOffset = BaseArea.INITVALUE
|
||||
_chassicInfoAreaOffset = BaseArea.INITVALUE
|
||||
_multiRecordAreaOffset = BaseArea.INITVALUE
|
||||
_bindata = None
|
||||
_bodybin = None
|
||||
_version = BaseArea.COMMON_HEAD_VERSION
|
||||
_zeroCheckSum = None
|
||||
|
||||
def __str__(self):
|
||||
tmpstr = ""
|
||||
if self.boardInfoArea.isPresent:
|
||||
tmpstr += "\nboardinfoarea: \n"
|
||||
tmpstr += self.boardInfoArea.__str__()
|
||||
if self.productInfoArea.isPresent:
|
||||
tmpstr += "\nproductinfoarea: \n"
|
||||
tmpstr += self.productInfoArea.__str__()
|
||||
return tmpstr
|
||||
|
||||
def decodeBin(self, eeprom):
|
||||
commonHead = eeprom[0:8]
|
||||
d_print("decode version %x" % ord(commonHead[0]))
|
||||
if self.COMMON_HEAD_VERSION != commonHead[0]:
|
||||
raise FruException("HEAD VERSION error,not Fru format!", -10)
|
||||
if FruUtil.checksum(commonHead[0:7]) != ord(commonHead[7]):
|
||||
strtemp = "check header checksum error [cal:%02x data:%02x]" % (
|
||||
FruUtil.checksum(commonHead[0:7]), ord(commonHead[7]))
|
||||
raise FruException(strtemp, -3)
|
||||
if commonHead[1] != self.INITVALUE:
|
||||
d_print("Internal Use Area is present")
|
||||
self.internalUseArea = InternalUseArea(
|
||||
name="Internal Use Area", size=self.SUGGESTED_SIZE_INTERNAL_USE_AREA)
|
||||
self.internalUseArea.isPresent = True
|
||||
self.internalUserAreaOffset = ord(commonHead[1])
|
||||
self.internalUseArea.data = eeprom[self.internalUserAreaOffset * 8: (
|
||||
self.internalUserAreaOffset * 8 + self.internalUseArea.size)]
|
||||
if commonHead[2] != self.INITVALUE:
|
||||
d_print("Chassis Info Area is present")
|
||||
self.chassisInfoArea = ChassisInfoArea(
|
||||
name="Chassis Info Area", size=self.SUGGESTED_SIZE_CHASSIS_INFO_AREA)
|
||||
self.chassisInfoArea.isPresent = True
|
||||
self.chassicInfoAreaOffset = ord(commonHead[2])
|
||||
self.chassisInfoArea.data = eeprom[self.chassicInfoAreaOffset * 8: (
|
||||
self.chassicInfoAreaOffset * 8 + self.chassisInfoArea.size)]
|
||||
if commonHead[3] != self.INITVALUE:
|
||||
self.boardInfoArea = BoardInfoArea(
|
||||
name="Board Info Area", size=self.SUGGESTED_SIZE_BOARD_INFO_AREA)
|
||||
self.boardInfoArea.isPresent = True
|
||||
self.boardInfoAreaOffset = ord(commonHead[3])
|
||||
self.boardInfoArea.size = ord(
|
||||
eeprom[self.boardInfoAreaOffset * 8 + 1]) * 8
|
||||
d_print("Board Info Area is present size:%d" %
|
||||
(self.boardInfoArea.size))
|
||||
self.boardInfoArea.data = eeprom[self.boardInfoAreaOffset * 8: (
|
||||
self.boardInfoAreaOffset * 8 + self.boardInfoArea.size)]
|
||||
if FruUtil.checksum(self.boardInfoArea.data[:-1]) != ord(self.boardInfoArea.data[-1:]):
|
||||
print "check boardInfoArea checksum error[cal:%02x data:%02x]" % \
|
||||
(FruUtil.checksum(
|
||||
self.boardInfoArea.data[:-1]), ord(self.boardInfoArea.data[-1:]))
|
||||
sys.exit(-1)
|
||||
self.boardInfoArea.decodedata()
|
||||
if commonHead[4] != self.INITVALUE:
|
||||
d_print("Product Info Area is present")
|
||||
self.productInfoArea = ProductInfoArea(
|
||||
name="Product Info Area ", size=self.SUGGESTED_SIZE_PRODUCT_INFO_AREA)
|
||||
self.productInfoArea.isPresent = True
|
||||
self.productinfoAreaOffset = ord(commonHead[4])
|
||||
d_print("length offset value: %02x" %
|
||||
ord(eeprom[self.productinfoAreaOffset * 8 + 1]))
|
||||
self.productInfoArea.size = ord(
|
||||
eeprom[self.productinfoAreaOffset * 8 + 1]) * 8
|
||||
d_print("Product Info Area is present size:%d" %
|
||||
(self.productInfoArea.size))
|
||||
|
||||
self.productInfoArea.data = eeprom[self.productinfoAreaOffset * 8: (
|
||||
self.productinfoAreaOffset * 8 + self.productInfoArea.size)]
|
||||
if FruUtil.checksum(self.productInfoArea.data[:-1]) != ord(self.productInfoArea.data[-1:]):
|
||||
strtmp = "check productInfoArea checksum error [cal:%02x data:%02x]" % (
|
||||
FruUtil.checksum(self.productInfoArea.data[:-1]), ord(self.productInfoArea.data[-1:]))
|
||||
raise FruException(strtmp, -3)
|
||||
self.productInfoArea.decodedata()
|
||||
if commonHead[5] != self.INITVALUE:
|
||||
self.multiRecordArea = MultiRecordArea(
|
||||
name="MultiRecord record Area ")
|
||||
d_print("MultiRecord record present")
|
||||
self.multiRecordArea.isPresent = True
|
||||
self.multiRecordAreaOffset = ord(commonHead[5])
|
||||
self.multiRecordArea.data = eeprom[self.multiRecordAreaOffset * 8: (
|
||||
self.multiRecordAreaOffset * 8 + self.multiRecordArea.size)]
|
||||
|
||||
def initDefault(self):
|
||||
self.version = self.COMMON_HEAD_VERSION
|
||||
self.internalUserAreaOffset = self.INITVALUE
|
||||
self.chassicInfoAreaOffset = self.INITVALUE
|
||||
self.boardInfoAreaOffset = self.INITVALUE
|
||||
self.productinfoAreaOffset = self.INITVALUE
|
||||
self.multiRecordAreaOffset = self.INITVALUE
|
||||
self.PAD = self.INITVALUE
|
||||
self.zeroCheckSum = self.INITVALUE
|
||||
self.offset = self.SUGGESTED_SIZE_COMMON_HEADER
|
||||
self.productInfoArea = None
|
||||
self.internalUseArea = None
|
||||
self.boardInfoArea = None
|
||||
self.chassisInfoArea = None
|
||||
self.multiRecordArea = None
|
||||
# self.recalcute()
|
||||
|
||||
@property
|
||||
def version(self):
|
||||
return self._version
|
||||
|
||||
@version.setter
|
||||
def version(self, name):
|
||||
self._version = name
|
||||
|
||||
@property
|
||||
def internalUserAreaOffset(self):
|
||||
return self._internalUserAreaOffset
|
||||
|
||||
@internalUserAreaOffset.setter
|
||||
def internalUserAreaOffset(self, obj):
|
||||
self._internalUserAreaOffset = obj
|
||||
|
||||
@property
|
||||
def chassicInfoAreaOffset(self):
|
||||
return self._chassicInfoAreaOffset
|
||||
|
||||
@chassicInfoAreaOffset.setter
|
||||
def chassicInfoAreaOffset(self, obj):
|
||||
self._chassicInfoAreaOffset = obj
|
||||
|
||||
@property
|
||||
def productinfoAreaOffset(self):
|
||||
return self._productinfoAreaOffset
|
||||
|
||||
@productinfoAreaOffset.setter
|
||||
def productinfoAreaOffset(self, obj):
|
||||
self._productinfoAreaOffset = obj
|
||||
|
||||
@property
|
||||
def boardInfoAreaOffset(self):
|
||||
return self._boardInfoAreaOffset
|
||||
|
||||
@boardInfoAreaOffset.setter
|
||||
def boardInfoAreaOffset(self, obj):
|
||||
self._boardInfoAreaOffset = obj
|
||||
|
||||
@property
|
||||
def multiRecordAreaOffset(self):
|
||||
return self._multiRecordAreaOffset
|
||||
|
||||
@multiRecordAreaOffset.setter
|
||||
def multiRecordAreaOffset(self, obj):
|
||||
self._multiRecordAreaOffset = obj
|
||||
|
||||
@property
|
||||
def zeroCheckSum(self):
|
||||
return self._zeroCheckSum
|
||||
|
||||
@zeroCheckSum.setter
|
||||
def zeroCheckSum(self, obj):
|
||||
self._zeroCheckSum = obj
|
||||
|
||||
@property
|
||||
def productInfoArea(self):
|
||||
return self._ProductInfoArea
|
||||
|
||||
@productInfoArea.setter
|
||||
def productInfoArea(self, obj):
|
||||
self._ProductInfoArea = obj
|
||||
|
||||
@property
|
||||
def internalUseArea(self):
|
||||
return self._InternalUseArea
|
||||
|
||||
@internalUseArea.setter
|
||||
def internalUseArea(self, obj):
|
||||
self.internalUseArea = obj
|
||||
|
||||
@property
|
||||
def boardInfoArea(self):
|
||||
return self._BoardInfoArea
|
||||
|
||||
@boardInfoArea.setter
|
||||
def boardInfoArea(self, obj):
|
||||
self._BoardInfoArea = obj
|
||||
|
||||
@property
|
||||
def chassisInfoArea(self):
|
||||
return self._ChassisInfoArea
|
||||
|
||||
@chassisInfoArea.setter
|
||||
def chassisInfoArea(self, obj):
|
||||
self._ChassisInfoArea = obj
|
||||
|
||||
@property
|
||||
def multiRecordArea(self):
|
||||
return self._multiRecordArea
|
||||
|
||||
@multiRecordArea.setter
|
||||
def multiRecordArea(self, obj):
|
||||
self._multiRecordArea = obj
|
||||
|
||||
@property
|
||||
def bindata(self):
|
||||
return self._bindata
|
||||
|
||||
@bindata.setter
|
||||
def bindata(self, obj):
|
||||
self._bindata = obj
|
||||
|
||||
@property
|
||||
def bodybin(self):
|
||||
return self._bodybin
|
||||
|
||||
@bodybin.setter
|
||||
def bodybin(self, obj):
|
||||
self._bodybin = obj
|
||||
|
||||
def recalcuteCommonHead(self):
|
||||
self.bindata = ""
|
||||
self.offset = self.SUGGESTED_SIZE_COMMON_HEADER
|
||||
d_print("common Header %d" % self.offset)
|
||||
if self.internalUseArea is not None and self.internalUseArea.isPresent:
|
||||
self.internalUserAreaOffset = self.offset / 8
|
||||
self.offset += self.internalUseArea.size
|
||||
d_print("internalUseArea is present offset:%d" % self.offset)
|
||||
|
||||
if self.chassisInfoArea is not None and self.chassisInfoArea.isPresent:
|
||||
self.chassicInfoAreaOffset = self.offset / 8
|
||||
self.offset += self.chassisInfoArea.size
|
||||
d_print("chassisInfoArea is present offset:%d" % self.offset)
|
||||
|
||||
if self.boardInfoArea is not None and self.boardInfoArea.isPresent:
|
||||
self.boardInfoAreaOffset = self.offset / 8
|
||||
self.offset += self.boardInfoArea.size
|
||||
d_print("boardInfoArea is present offset:%d" % self.offset)
|
||||
d_print("boardInfoArea is present size:%d" %
|
||||
self.boardInfoArea.size)
|
||||
|
||||
if self.productInfoArea is not None and self.productInfoArea.isPresent:
|
||||
self.productinfoAreaOffset = self.offset / 8
|
||||
self.offset += self.productInfoArea.size
|
||||
d_print("productInfoArea is present offset:%d" % self.offset)
|
||||
|
||||
if self.multiRecordArea is not None and self.multiRecordArea.isPresent:
|
||||
self.multiRecordAreaOffset = self.offset / 8
|
||||
d_print("multiRecordArea is present offset:%d" % self.offset)
|
||||
|
||||
if self.internalUserAreaOffset == self.INITVALUE:
|
||||
self.internalUserAreaOffset = 0
|
||||
if self.productinfoAreaOffset == self.INITVALUE:
|
||||
self.productinfoAreaOffset = 0
|
||||
if self.chassicInfoAreaOffset == self.INITVALUE:
|
||||
self.chassicInfoAreaOffset = 0
|
||||
if self.boardInfoAreaOffset == self.INITVALUE:
|
||||
self.boardInfoAreaOffset = 0
|
||||
if self.multiRecordAreaOffset == self.INITVALUE:
|
||||
self.multiRecordAreaOffset = 0
|
||||
|
||||
self.zeroCheckSum = (0x100 - ord(self.version) - self.internalUserAreaOffset - self.chassicInfoAreaOffset - self.productinfoAreaOffset
|
||||
- self.boardInfoAreaOffset - self.multiRecordAreaOffset) & 0xff
|
||||
d_print("zerochecksum:%x" % self.zeroCheckSum)
|
||||
self.data = self.version + chr(self.internalUserAreaOffset) + chr(self.chassicInfoAreaOffset) + chr(
|
||||
self.boardInfoAreaOffset) + chr(self.productinfoAreaOffset) + chr(self.multiRecordAreaOffset) + self.INITVALUE + chr(self.zeroCheckSum)
|
||||
|
||||
self.bindata = self.data + self.bodybin
|
||||
totallen = len(self.bindata)
|
||||
d_print("totallen %d" % totallen)
|
||||
if (totallen < 256):
|
||||
self.bindata = self.bindata.ljust(256, self.INITVALUE)
|
||||
else:
|
||||
raise FruException('bin data more than 256', -2)
|
||||
|
||||
def recalcutebin(self):
|
||||
self.bodybin = ""
|
||||
if self.internalUseArea is not None and self.internalUseArea.isPresent:
|
||||
d_print("internalUseArea present")
|
||||
self.bodybin += self.internalUseArea.data
|
||||
if self.chassisInfoArea is not None and self.chassisInfoArea.isPresent:
|
||||
d_print("chassisInfoArea present")
|
||||
self.bodybin += self.chassisInfoArea.data
|
||||
if self.boardInfoArea is not None and self.boardInfoArea.isPresent:
|
||||
d_print("boardInfoArea present")
|
||||
self.boardInfoArea.recalcute()
|
||||
self.bodybin += self.boardInfoArea.data
|
||||
if self.productInfoArea is not None and self.productInfoArea.isPresent:
|
||||
d_print("productInfoAreapresent")
|
||||
self.productInfoArea.recalcute()
|
||||
self.bodybin += self.productInfoArea.data
|
||||
if self.multiRecordArea is not None and self.multiRecordArea.isPresent:
|
||||
d_print("multiRecordArea present")
|
||||
self.bodybin += self.productInfoArea.data
|
||||
|
||||
def recalcute(self):
|
||||
self.recalcutebin()
|
||||
self.recalcuteCommonHead()
|
@ -0,0 +1,2 @@
|
||||
CONSOLE_SPEED=115200
|
||||
ONIE_PLATFORM_EXTRA_CMDLINE_LINUX="intel_pstate=disable intel_idle.max_cstate=0 modprobe.blacklist=fpga_pcie_i2c"
|
@ -0,0 +1,7 @@
|
||||
m0 load 0 0x3800 /usr/share/sonic/platform/custom_led.bin
|
||||
|
||||
led auto on
|
||||
|
||||
led start
|
||||
|
||||
linkscan spbm=all force=all interval=250000
|
BIN
device/ragile/x86_64-ragile_ra-b6510-32c-r0/linkscan_led.bin
Normal file
BIN
device/ragile/x86_64-ragile_ra-b6510-32c-r0/linkscan_led.bin
Normal file
Binary file not shown.
63
device/ragile/x86_64-ragile_ra-b6510-32c-r0/minigraph.xml
Normal file
63
device/ragile/x86_64-ragile_ra-b6510-32c-r0/minigraph.xml
Normal file
@ -0,0 +1,63 @@
|
||||
<DeviceMiniGraph xmlns:i="http://www.w3.org/2001/XMLSchema-instance" xmlns="Microsoft.Search.Autopilot.Evolution">
|
||||
<CpgDec>
|
||||
</CpgDec>
|
||||
<DpgDec>
|
||||
<DeviceDataPlaneInfo>
|
||||
<IPSecTunnels/>
|
||||
<LoopbackIPInterfaces/>
|
||||
<ManagementIPInterfaces xmlns:a="http://schemas.datacontract.org/2004/07/Microsoft.Search.Autopilot.Evolution">
|
||||
</ManagementIPInterfaces>
|
||||
<MplsInterfaces/>
|
||||
<MplsTeInterfaces/>
|
||||
<RsvpInterfaces/>
|
||||
<Hostname>switch2</Hostname>
|
||||
<PortChannelInterfaces/>
|
||||
<VlanInterfaces/>
|
||||
<IPInterfaces/>
|
||||
<DataAcls/>
|
||||
<AclInterfaces/>
|
||||
<DownstreamSummaries/>
|
||||
<DownstreamSummarySet xmlns:a="http://schemas.datacontract.org/2004/07/Microsoft.Search.Autopilot.Evolution"/>
|
||||
</DeviceDataPlaneInfo>
|
||||
</DpgDec>
|
||||
<PngDec>
|
||||
<Devices>
|
||||
<Device i:type="LeafRouter">
|
||||
<Hostname>switch2</Hostname>
|
||||
<HwSku>RA-B6510-32C</HwSku>
|
||||
</Device>
|
||||
</Devices>
|
||||
</PngDec>
|
||||
<MetadataDeclaration>
|
||||
<Devices xmlns:a="http://schemas.datacontract.org/2004/07/Microsoft.Search.Autopilot.Evolution">
|
||||
<a:DeviceMetadata>
|
||||
<a:Name>switch2</a:Name>
|
||||
<a:Properties>
|
||||
<a:DeviceProperty>
|
||||
<a:Name>DhcpResources</a:Name>
|
||||
<a:Reference i:nil="true"/>
|
||||
<a:Value></a:Value>
|
||||
</a:DeviceProperty>
|
||||
<a:DeviceProperty>
|
||||
<a:Name>NtpResources</a:Name>
|
||||
<a:Reference i:nil="true"/>
|
||||
<a:Value>0.debian.pool.ntp.org;1.debian.pool.ntp.org;2.debian.pool.ntp.org;3.debian.pool.ntp.org</a:Value>
|
||||
</a:DeviceProperty>
|
||||
<a:DeviceProperty>
|
||||
<a:Name>SyslogResources</a:Name>
|
||||
<a:Reference i:nil="true"/>
|
||||
<a:Value></a:Value>
|
||||
</a:DeviceProperty>
|
||||
<a:DeviceProperty>
|
||||
<a:Name>ErspanDestinationIpv4</a:Name>
|
||||
<a:Reference i:nil="true"/>
|
||||
<a:Value>2.2.2.2</a:Value>
|
||||
</a:DeviceProperty>
|
||||
</a:Properties>
|
||||
</a:DeviceMetadata>
|
||||
</Devices>
|
||||
<Properties xmlns:a="http://schemas.datacontract.org/2004/07/Microsoft.Search.Autopilot.Evolution"/>
|
||||
</MetadataDeclaration>
|
||||
<Hostname>switch2</Hostname>
|
||||
<HwSku>RA-B6510-32C</HwSku>
|
||||
</DeviceMiniGraph>
|
315
device/ragile/x86_64-ragile_ra-b6510-32c-r0/monitor.py
Normal file
315
device/ragile/x86_64-ragile_ra-b6510-32c-r0/monitor.py
Normal file
@ -0,0 +1,315 @@
|
||||
#!/usr/bin/python
|
||||
# -*- coding: UTF-8 -*-
|
||||
# * onboard temperature sensors
|
||||
# * FAN trays
|
||||
# * PSU
|
||||
#
|
||||
import os
|
||||
import xml.etree.ElementTree as ET
|
||||
import glob
|
||||
from fru import *
|
||||
from fantlv import *
|
||||
|
||||
|
||||
|
||||
MAILBOX_DIR = "/sys/bus/i2c/devices/"
|
||||
CONFIG_NAME = "dev.xml"
|
||||
|
||||
def getPMCreg(location):
|
||||
retval = 'ERR'
|
||||
if (not os.path.isfile(location)):
|
||||
return "%s %s notfound"% (retval , location)
|
||||
try:
|
||||
with open(location, 'r') as fd:
|
||||
retval = fd.read()
|
||||
except Exception as error:
|
||||
pass
|
||||
|
||||
retval = retval.rstrip('\r\n')
|
||||
retval = retval.lstrip(" ")
|
||||
return retval
|
||||
# Get a mailbox register
|
||||
def get_pmc_register(reg_name):
|
||||
retval = 'ERR'
|
||||
mb_reg_file = MAILBOX_DIR + reg_name
|
||||
filepath = glob.glob(mb_reg_file)
|
||||
if(len(filepath) == 0):
|
||||
return "%s %s notfound"% (retval , mb_reg_file)
|
||||
mb_reg_file = filepath[0]
|
||||
if (not os.path.isfile(mb_reg_file)):
|
||||
#print mb_reg_file, 'not found !'
|
||||
return "%s %s notfound"% (retval , mb_reg_file)
|
||||
try:
|
||||
with open(mb_reg_file, 'r') as fd:
|
||||
retval = fd.read()
|
||||
except Exception as error:
|
||||
pass
|
||||
|
||||
retval = retval.rstrip('\r\n')
|
||||
retval = retval.lstrip(" ")
|
||||
return retval
|
||||
|
||||
class checktype():
|
||||
def __init__(self, test1):
|
||||
self.test1 = test1
|
||||
@staticmethod
|
||||
def check(name,location, bit, value, tips , err1):
|
||||
psu_status = int(get_pmc_register(location),16)
|
||||
val = (psu_status & (1<< bit)) >> bit
|
||||
if (val != value):
|
||||
err1["errmsg"] = tips
|
||||
err1["code"] = -1
|
||||
return -1
|
||||
else:
|
||||
err1["errmsg"] = "none"
|
||||
err1["code"] = 0
|
||||
return 0
|
||||
@staticmethod
|
||||
def getValue(location, bit , type):
|
||||
value_t = get_pmc_register(location)
|
||||
if value_t.startswith("ERR") :
|
||||
return value_t
|
||||
if (type == 1):
|
||||
return float(value_t)/1000
|
||||
elif (type == 2):
|
||||
return float(value_t)/100
|
||||
elif (type == 3):
|
||||
psu_status = int(value_t,16)
|
||||
return (psu_status & (1<< bit)) >> bit
|
||||
elif (type == 4):
|
||||
return int(value_t,10)
|
||||
elif (type == 5):
|
||||
return float(value_t)/1000/1000
|
||||
else:
|
||||
return value_t;
|
||||
#######temp
|
||||
@staticmethod
|
||||
def getTemp(self, name, location , ret_t):
|
||||
ret2 = self.getValue(location + "temp1_input" ," " ,1);
|
||||
ret3 = self.getValue(location + "temp1_max" ," ", 1);
|
||||
ret4 = self.getValue(location + "temp1_max_hyst" ," ", 1);
|
||||
ret_t["temp1_input"] = ret2
|
||||
ret_t["temp1_max"] = ret3
|
||||
ret_t["temp1_max_hyst"] = ret4
|
||||
@staticmethod
|
||||
def getLM75(name, location, result):
|
||||
c1=checktype
|
||||
r1={}
|
||||
c1.getTemp(c1, name, location, r1)
|
||||
result[name] = r1
|
||||
##########fanFRU
|
||||
@staticmethod
|
||||
def decodeBinByValue(retval):
|
||||
fru = ipmifru()
|
||||
fru.decodeBin(retval)
|
||||
return fru
|
||||
|
||||
@staticmethod
|
||||
def printbinvalue(b):
|
||||
index = 0
|
||||
print " ",
|
||||
for width in range(16):
|
||||
print "%02x " % width,
|
||||
print ""
|
||||
for i in range(0, len(b)):
|
||||
if index % 16 == 0:
|
||||
print " "
|
||||
print " %02x " % i,
|
||||
print "%02x " % ord(b[i]),
|
||||
index += 1
|
||||
print ""
|
||||
|
||||
@staticmethod
|
||||
def getfruValue(val):
|
||||
try:
|
||||
binval = checktype.getValue(val, 0 , 0)
|
||||
if binval.startswith("ERR"):
|
||||
return binval
|
||||
fanpro = {}
|
||||
ret = checktype.decodeBinByValue(binval)
|
||||
fanpro['fan_type'] = ret.productInfoArea.productName
|
||||
fanpro['hw_version'] = ret.productInfoArea.productVersion
|
||||
fanpro['sn'] = ret.productInfoArea.productSerialNumber
|
||||
fanpro['fanid'] = ret.productInfoArea.productextra2
|
||||
return fanpro
|
||||
except Exception as error:
|
||||
return "ERR " + str(error)
|
||||
|
||||
@staticmethod
|
||||
def getslottlvValue(val):
|
||||
try:
|
||||
binval = checktype.getValue(val, 0 , 0)
|
||||
if binval.startswith("ERR"):
|
||||
return binval
|
||||
slotpro = {}
|
||||
slottlv = fan_tlv()
|
||||
rets = slottlv.decode(binval)
|
||||
if len(rets) == 0:
|
||||
raise Exception("decode fan tlv fail")
|
||||
slotpro['slot_type'] = slottlv.typename
|
||||
slotpro['hw_version'] = slottlv.typehwinfo
|
||||
slotpro['sn'] = slottlv.typesn
|
||||
slotpro['slotid'] = slottlv.typedevtype
|
||||
return slotpro
|
||||
except Exception as error:
|
||||
return "ERR " + str(error)
|
||||
|
||||
@staticmethod
|
||||
def getslotfruValue(val):
|
||||
try:
|
||||
binval = checktype.getValue(val, 0 , 0)
|
||||
if binval.startswith("ERR"):
|
||||
return binval
|
||||
slotpro = {}
|
||||
ret = checktype.decodeBinByValue(binval)
|
||||
slotpro['slot_type'] = ret.boardInfoArea.boardProductName
|
||||
slotpro['hw_version'] = ret.boardInfoArea.boardextra1
|
||||
slotpro['sn'] = ret.boardInfoArea.boardSerialNumber
|
||||
return slotpro
|
||||
except Exception as error:
|
||||
return "ERR " + str(error)
|
||||
|
||||
|
||||
class status():
|
||||
def __init__(self, productname):
|
||||
self.productname = productname
|
||||
|
||||
@staticmethod
|
||||
def getETroot(filename):
|
||||
tree = ET.parse(filename)
|
||||
root = tree.getroot()
|
||||
return root;
|
||||
|
||||
@staticmethod
|
||||
def getDecodValue(collection, decode):
|
||||
decodes = collection.find('decode')
|
||||
testdecode = decodes.find(decode)
|
||||
test={}
|
||||
for neighbor in testdecode.iter('code'):
|
||||
test[neighbor.attrib["key"]]=neighbor.attrib["value"]
|
||||
return test
|
||||
@staticmethod
|
||||
def getfileValue(location):
|
||||
return checktype.getValue(location," "," ")
|
||||
@staticmethod
|
||||
def getETValue(a, filename, tagname):
|
||||
root = status.getETroot(filename)
|
||||
for neighbor in root.iter(tagname):
|
||||
prob_t = {}
|
||||
prob_t = neighbor.attrib
|
||||
prob_t['errcode']= 0
|
||||
prob_t['errmsg'] = ''
|
||||
for pros in neighbor.iter("property"):
|
||||
ret = dict(neighbor.attrib.items() + pros.attrib.items())
|
||||
if ret.get('e2type') == 'fru' and ret.get("name") == "fru":
|
||||
fruval = checktype.getfruValue(ret["location"])
|
||||
if isinstance(fruval, str) and fruval.startswith("ERR"):
|
||||
prob_t['errcode']= -1
|
||||
prob_t['errmsg']= fruval
|
||||
else:
|
||||
prob_t.update(fruval)
|
||||
if ret.get("name") == "slot" and ret.get('e2type') == 'tlv':
|
||||
slotval = checktype.getslottlvValue(ret["location"])
|
||||
if isinstance(slotval, str) and slotval.startswith("ERR"):
|
||||
prob_t['errcode']= -1
|
||||
prob_t['errmsg']= slotval
|
||||
else:
|
||||
prob_t.update(slotval)
|
||||
if ret.get("name") == "slot" and ret.get('e2type') == 'fru':
|
||||
slotval = checktype.getslotfruValue(ret["location"])
|
||||
if isinstance(slotval, str) and slotval.startswith("ERR"):
|
||||
prob_t['errcode']= -1
|
||||
prob_t['errmsg']= slotval
|
||||
else:
|
||||
prob_t.update(slotval)
|
||||
|
||||
if ('type' not in ret.keys()):
|
||||
val = "0";
|
||||
else:
|
||||
val = ret["type"]
|
||||
if ('bit' not in ret.keys()):
|
||||
bit = "0";
|
||||
else:
|
||||
bit = ret["bit"]
|
||||
s = checktype.getValue(ret["location"], int(bit),int(val))
|
||||
if isinstance(s, str) and s.startswith("ERR"):
|
||||
prob_t['errcode']= -1
|
||||
prob_t['errmsg']= s
|
||||
if ('default' in ret.keys()):
|
||||
rt = status.getDecodValue(root,ret['decode'])
|
||||
prob_t['errmsg']= rt[str(s)]
|
||||
if str(s) != ret["default"]:
|
||||
prob_t['errcode']= -1
|
||||
break;
|
||||
else:
|
||||
if ('decode' in ret.keys()):
|
||||
rt = status.getDecodValue(root,ret['decode'])
|
||||
if(ret['decode'] == "psutype" and s.replace("\x00","").rstrip() not in rt.keys()):
|
||||
prob_t['errcode']= -1
|
||||
prob_t['errmsg'] = '%s'% ("Not supported PSU type")
|
||||
else:
|
||||
s = rt[str(s).replace("\x00","").rstrip()]
|
||||
name = ret["name"]
|
||||
prob_t[name]=str(s)
|
||||
a.append(prob_t)
|
||||
@staticmethod
|
||||
def getCPUValue(a, filename, tagname):
|
||||
root = status.getETroot(filename)
|
||||
for neighbor in root.iter(tagname):
|
||||
location = neighbor.attrib["location"]
|
||||
L=[]
|
||||
for dirpath, dirnames, filenames in os.walk(location):
|
||||
for file in filenames :
|
||||
if file.endswith("input"):
|
||||
L.append(os.path.join(dirpath, file))
|
||||
L =sorted(L,reverse=False)
|
||||
for i in range(len(L)):
|
||||
prob_t = {}
|
||||
prob_t["name"] = getPMCreg("%s/temp%d_label"%(location,i+1))
|
||||
prob_t["temp"] = float(getPMCreg("%s/temp%d_input"%(location,i+1)))/1000
|
||||
prob_t["alarm"] = float(getPMCreg("%s/temp%d_crit_alarm"%(location,i+1)))/1000
|
||||
prob_t["crit"] = float(getPMCreg("%s/temp%d_crit"%(location,i+1)))/1000
|
||||
prob_t["max"] = float(getPMCreg("%s/temp%d_max"%(location,i+1)))/1000
|
||||
a.append(prob_t)
|
||||
|
||||
@staticmethod
|
||||
def getFileName():
|
||||
return os.path.dirname(os.path.realpath(__file__)) + "/"+ CONFIG_NAME
|
||||
@staticmethod
|
||||
def getFan(ret):
|
||||
_filename = status.getFileName()
|
||||
_tagname = "fan"
|
||||
status.getvalue(ret, _filename, _tagname)
|
||||
@staticmethod
|
||||
def checkFan(ret):
|
||||
_filename = status.getFileName()
|
||||
# _filename = "/usr/local/bin/" + status.getFileName()
|
||||
_tagname = "fan"
|
||||
status.getETValue(ret, _filename, _tagname)
|
||||
@staticmethod
|
||||
def getTemp(ret):
|
||||
_filename = status.getFileName()
|
||||
#_filename = "/usr/local/bin/" + status.getFileName()
|
||||
_tagname = "temp"
|
||||
status.getETValue(ret, _filename, _tagname)
|
||||
@staticmethod
|
||||
def getPsu(ret):
|
||||
_filename = status.getFileName()
|
||||
# _filename = "/usr/local/bin/" + status.getFileName()
|
||||
_tagname = "psu"
|
||||
status.getETValue(ret, _filename, _tagname)
|
||||
|
||||
@staticmethod
|
||||
def getcputemp(ret):
|
||||
_filename = status.getFileName()
|
||||
_tagname = "cpus"
|
||||
status.getCPUValue(ret, _filename, _tagname)
|
||||
|
||||
@staticmethod
|
||||
def checkSlot(ret):
|
||||
_filename = status.getFileName()
|
||||
# _filename = "/usr/local/bin/" + status.getFileName()
|
||||
_tagname = "slot"
|
||||
status.getETValue(ret, _filename, _tagname)
|
||||
|
||||
|
@ -0,0 +1,67 @@
|
||||
{
|
||||
"XCVR": {
|
||||
"xcvr_present": {
|
||||
"i2c": {
|
||||
"valmap-SFP28": {
|
||||
"1": true,
|
||||
"0": false
|
||||
},
|
||||
"valmap-QSFP28": {
|
||||
"1": true,
|
||||
"0": false
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
"PSU": {
|
||||
"psu_present": {
|
||||
"i2c": {
|
||||
"valmap": {
|
||||
"1": true,
|
||||
"0": false
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
"psu_power_good": {
|
||||
"i2c": {
|
||||
"valmap": {
|
||||
"1": true,
|
||||
"0": false
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
"psu_fan_dir": {
|
||||
"i2c": {
|
||||
"valmap": {
|
||||
"F2B": "EXHAUST",
|
||||
"B2F": "INTAKE"
|
||||
}
|
||||
}
|
||||
},
|
||||
"PSU_FAN_MAX_SPEED": "18000"
|
||||
},
|
||||
|
||||
"FAN": {
|
||||
"direction": {
|
||||
"i2c": {
|
||||
"valmap": {
|
||||
"1": "INTAKE",
|
||||
"0": "EXHAUST"
|
||||
}
|
||||
}
|
||||
},
|
||||
"present": {
|
||||
"i2c": {
|
||||
"valmap": {
|
||||
"1": true,
|
||||
"0": false
|
||||
}
|
||||
}
|
||||
},
|
||||
"duty_cycle_to_pwm": "lambda dc: dc*255/100",
|
||||
"pwm_to_duty_cycle": "lambda pwm: pwm*100/255"
|
||||
}
|
||||
}
|
4471
device/ragile/x86_64-ragile_ra-b6510-32c-r0/pddf/pddf-device.json
Executable file
4471
device/ragile/x86_64-ragile_ra-b6510-32c-r0/pddf/pddf-device.json
Executable file
File diff suppressed because it is too large
Load Diff
@ -0,0 +1 @@
|
||||
broadcom
|
@ -0,0 +1,13 @@
|
||||
#!/usr/bin/env python
|
||||
|
||||
try:
|
||||
from sonic_eeprom import eeprom_tlvinfo
|
||||
except ImportError as e:
|
||||
raise ImportError (str(e) + "- required module not found")
|
||||
|
||||
|
||||
class board(eeprom_tlvinfo.TlvInfoDecoder):
|
||||
|
||||
def __init__(self, name, path, cpld_root, ro):
|
||||
self.eeprom_path = "/sys/bus/i2c/devices/1-0056/eeprom"
|
||||
super(board, self).__init__(self.eeprom_path, 0, '', True)
|
@ -0,0 +1,63 @@
|
||||
#
|
||||
# psuutil.py
|
||||
# Platform-specific PSU status interface for SONiC
|
||||
#
|
||||
|
||||
try:
|
||||
from sonic_psu.psu_base import PsuBase
|
||||
except ImportError as e:
|
||||
raise ImportError(str(e) + "- required module not found")
|
||||
|
||||
|
||||
class PsuUtil(PsuBase):
|
||||
"""Platform-specific PSUutil class"""
|
||||
|
||||
def __init__(self):
|
||||
PsuBase.__init__(self)
|
||||
|
||||
def get_num_psus(self):
|
||||
return 2
|
||||
|
||||
def get_psu_status(self, index):
|
||||
if index != 1 and index != 2:
|
||||
return False
|
||||
|
||||
psu_path = "/sys/bus/i2c/devices/6-000d/psu_status"
|
||||
|
||||
try:
|
||||
data = open(psu_path, "rb")
|
||||
except IOError:
|
||||
return False
|
||||
|
||||
result = int(data.read(2), 16)
|
||||
data.close()
|
||||
|
||||
if index == 1 and (result & 0x2):
|
||||
return True
|
||||
|
||||
if index == 2 and (result & 0x20):
|
||||
return True
|
||||
|
||||
return False
|
||||
|
||||
def get_psu_presence(self, index):
|
||||
if index != 1 and index != 2:
|
||||
return False
|
||||
|
||||
psu_path = "/sys/bus/i2c/devices/6-000d/psu_status"
|
||||
|
||||
try:
|
||||
data = open(psu_path, "rb")
|
||||
except IOError:
|
||||
return False
|
||||
|
||||
result = int(data.read(2), 16)
|
||||
data.close()
|
||||
|
||||
if index == 1 and (result & 0x1) == 0:
|
||||
return True
|
||||
|
||||
if index == 2 and (result & 0x10) == 0:
|
||||
return True
|
||||
|
||||
return False
|
255
device/ragile/x86_64-ragile_ra-b6510-32c-r0/plugins/sfputil.py
Normal file
255
device/ragile/x86_64-ragile_ra-b6510-32c-r0/plugins/sfputil.py
Normal file
@ -0,0 +1,255 @@
|
||||
# sfputil.py
|
||||
#
|
||||
# Platform-specific SFP transceiver interface for SONiC
|
||||
#
|
||||
|
||||
try:
|
||||
import time
|
||||
import os
|
||||
from sonic_sfp.sfputilbase import SfpUtilBase
|
||||
except ImportError as e:
|
||||
raise ImportError("%s - required module not found" % str(e))
|
||||
|
||||
class SfpUtil(SfpUtilBase):
|
||||
"""Platform-specific SfpUtil class"""
|
||||
|
||||
PORT_START = 0
|
||||
PORT_END = 31
|
||||
PORTS_IN_BLOCK = 32
|
||||
|
||||
EEPROM_OFFSET = 32
|
||||
SFP_DEVICE_TYPE = "optoe2"
|
||||
QSFP_DEVICE_TYPE = "optoe1"
|
||||
I2C_MAX_ATTEMPT = 3
|
||||
|
||||
SFP_STATUS_INSERTED = '1'
|
||||
SFP_STATUS_REMOVED = '0'
|
||||
|
||||
_port_to_eeprom_mapping = {}
|
||||
port_to_i2cbus_mapping ={}
|
||||
port_dict = {}
|
||||
|
||||
@property
|
||||
def port_start(self):
|
||||
return self.PORT_START
|
||||
|
||||
@property
|
||||
def port_end(self):
|
||||
return self.PORT_END
|
||||
|
||||
@property
|
||||
def qsfp_ports(self):
|
||||
return range(0, self.PORTS_IN_BLOCK)
|
||||
|
||||
@property
|
||||
def port_to_eeprom_mapping(self):
|
||||
return self._port_to_eeprom_mapping
|
||||
|
||||
def __init__(self):
|
||||
for x in range(self.PORT_START, self.PORTS_IN_BLOCK):
|
||||
self.port_to_i2cbus_mapping[x] = (x + self.EEPROM_OFFSET)
|
||||
SfpUtilBase.__init__(self)
|
||||
|
||||
def _sfp_read_file_path(self, file_path, offset, num_bytes):
|
||||
attempts = 0
|
||||
while attempts < self.I2C_MAX_ATTEMPT:
|
||||
try:
|
||||
file_path.seek(offset)
|
||||
read_buf = file_path.read(num_bytes)
|
||||
except Exception:
|
||||
attempts += 1
|
||||
time.sleep(0.05)
|
||||
else:
|
||||
return True, read_buf
|
||||
return False, None
|
||||
|
||||
def _sfp_eeprom_present(self, sysfs_sfp_i2c_client_eeprompath, offset):
|
||||
"""Tries to read the eeprom file to determine if the
|
||||
device/sfp is present or not. If sfp present, the read returns
|
||||
valid bytes. If not, read returns error 'Connection timed out"""
|
||||
|
||||
if not os.path.exists(sysfs_sfp_i2c_client_eeprompath):
|
||||
return False
|
||||
else:
|
||||
with open(sysfs_sfp_i2c_client_eeprompath, "rb", buffering=0) as sysfsfile:
|
||||
rv, buf = self._sfp_read_file_path(sysfsfile, offset, 1)
|
||||
return rv
|
||||
|
||||
def _add_new_sfp_device(self, sysfs_sfp_i2c_adapter_path, devaddr, devtype):
|
||||
try:
|
||||
sysfs_nd_path = "%s/new_device" % sysfs_sfp_i2c_adapter_path
|
||||
|
||||
# Write device address to new_device file
|
||||
nd_file = open(sysfs_nd_path, "w")
|
||||
nd_str = "%s %s" % (devtype, hex(devaddr))
|
||||
nd_file.write(nd_str)
|
||||
nd_file.close()
|
||||
|
||||
except Exception as err:
|
||||
print("Error writing to new device file: %s" % str(err))
|
||||
return 1
|
||||
else:
|
||||
return 0
|
||||
|
||||
def _get_port_eeprom_path(self, port_num, devid):
|
||||
sysfs_i2c_adapter_base_path = ""
|
||||
|
||||
if port_num in self.port_to_eeprom_mapping.keys():
|
||||
sysfs_sfp_i2c_client_eeprom_path = self.port_to_eeprom_mapping[port_num]
|
||||
else:
|
||||
sysfs_i2c_adapter_base_path = "/sys/class/i2c-adapter"
|
||||
|
||||
i2c_adapter_id = self._get_port_i2c_adapter_id(port_num)
|
||||
if i2c_adapter_id is None:
|
||||
print("Error getting i2c bus num")
|
||||
return None
|
||||
|
||||
# Get i2c virtual bus path for the sfp
|
||||
sysfs_sfp_i2c_adapter_path = "%s/i2c-%s" % (sysfs_i2c_adapter_base_path,
|
||||
str(i2c_adapter_id))
|
||||
|
||||
# If i2c bus for port does not exist
|
||||
if not os.path.exists(sysfs_sfp_i2c_adapter_path):
|
||||
print("Could not find i2c bus %s. Driver not loaded?" % sysfs_sfp_i2c_adapter_path)
|
||||
return None
|
||||
|
||||
sysfs_sfp_i2c_client_path = "%s/%s-00%s" % (sysfs_sfp_i2c_adapter_path,
|
||||
str(i2c_adapter_id),
|
||||
hex(devid)[-2:])
|
||||
|
||||
# If sfp device is not present on bus, Add it
|
||||
if not os.path.exists(sysfs_sfp_i2c_client_path):
|
||||
if port_num in self.qsfp_ports:
|
||||
ret = self._add_new_sfp_device(
|
||||
sysfs_sfp_i2c_adapter_path, devid, self.QSFP_DEVICE_TYPE)
|
||||
else:
|
||||
ret = self._add_new_sfp_device(
|
||||
sysfs_sfp_i2c_adapter_path, devid, self.SFP_DEVICE_TYPE)
|
||||
if ret != 0:
|
||||
print("Error adding sfp device")
|
||||
return None
|
||||
|
||||
sysfs_sfp_i2c_client_eeprom_path = "%s/eeprom" % sysfs_sfp_i2c_client_path
|
||||
|
||||
return sysfs_sfp_i2c_client_eeprom_path
|
||||
|
||||
def _read_eeprom_specific_bytes(self, sysfsfile_eeprom, offset, num_bytes):
|
||||
eeprom_raw = []
|
||||
for i in range(0, num_bytes):
|
||||
eeprom_raw.append("0x00")
|
||||
|
||||
rv, raw = self._sfp_read_file_path(sysfsfile_eeprom, offset, num_bytes)
|
||||
if rv == False:
|
||||
return None
|
||||
|
||||
try:
|
||||
for n in range(0, num_bytes):
|
||||
eeprom_raw[n] = hex(ord(raw[n]))[2:].zfill(2)
|
||||
except Exception:
|
||||
return None
|
||||
|
||||
return eeprom_raw
|
||||
|
||||
def get_eeprom_dom_raw(self, port_num):
|
||||
if port_num in self.qsfp_ports:
|
||||
# QSFP DOM EEPROM is also at addr 0x50 and thus also stored in eeprom_ifraw
|
||||
return None
|
||||
else:
|
||||
# Read dom eeprom at addr 0x51
|
||||
return self._read_eeprom_devid(port_num, self.IDENTITY_EEPROM_ADDR, 256)
|
||||
|
||||
def get_presence(self, port_num):
|
||||
# Check for invalid port_num
|
||||
if port_num < self.port_start or port_num > self.port_end:
|
||||
return False
|
||||
|
||||
if port_num <= 7:
|
||||
presence_path = "/sys/bus/i2c/devices/8-0030/sfp_presence1"
|
||||
elif port_num >= 8 and port_num <= 15:
|
||||
presence_path = "/sys/bus/i2c/devices/8-0030/sfp_presence2"
|
||||
elif port_num >= 16 and port_num <= 23:
|
||||
presence_path = "/sys/bus/i2c/devices/8-0031/sfp_presence3"
|
||||
elif port_num >= 24 and port_num <= 31:
|
||||
presence_path = "/sys/bus/i2c/devices/8-0031/sfp_presence4"
|
||||
else:
|
||||
return False
|
||||
|
||||
try:
|
||||
data = open(presence_path, "rb")
|
||||
except IOError:
|
||||
return False
|
||||
|
||||
presence_data = data.read(2)
|
||||
if presence_data == "":
|
||||
return False
|
||||
result = int(presence_data, 16)
|
||||
data.close()
|
||||
|
||||
# ModPrsL is active low
|
||||
if result & (1 << (port_num % 8)) == 0:
|
||||
return True
|
||||
|
||||
return False
|
||||
|
||||
def get_low_power_mode(self, port_num):
|
||||
# Check for invalid port_num
|
||||
|
||||
return True
|
||||
|
||||
def set_low_power_mode(self, port_num, lpmode):
|
||||
# Check for invalid port_num
|
||||
|
||||
return True
|
||||
|
||||
def reset(self, port_num):
|
||||
# Check for invalid port_num
|
||||
if port_num < self.port_start or port_num > self.port_end:
|
||||
return False
|
||||
|
||||
return True
|
||||
|
||||
def get_transceiver_change_event(self, timeout=0):
|
||||
|
||||
start_time = time.time()
|
||||
currernt_port_dict = {}
|
||||
forever = False
|
||||
|
||||
if timeout == 0:
|
||||
forever = True
|
||||
elif timeout > 0:
|
||||
timeout = timeout / float(1000) # Convert to secs
|
||||
else:
|
||||
print ("get_transceiver_change_event:Invalid timeout value", timeout)
|
||||
return False, {}
|
||||
|
||||
end_time = start_time + timeout
|
||||
if start_time > end_time:
|
||||
print ('get_transceiver_change_event:' \
|
||||
'time wrap / invalid timeout value', timeout)
|
||||
|
||||
return False, {} # Time wrap or possibly incorrect timeout
|
||||
|
||||
while timeout >= 0:
|
||||
# Check for OIR events and return updated port_dict
|
||||
for x in range(self.PORT_START, self.PORTS_IN_BLOCK):
|
||||
if self.get_presence(x):
|
||||
currernt_port_dict[x] = self.SFP_STATUS_INSERTED
|
||||
else:
|
||||
currernt_port_dict[x] = self.SFP_STATUS_REMOVED
|
||||
if (currernt_port_dict == self.port_dict):
|
||||
if forever:
|
||||
time.sleep(1)
|
||||
else:
|
||||
timeout = end_time - time.time()
|
||||
if timeout >= 1:
|
||||
time.sleep(1) # We poll at 1 second granularity
|
||||
else:
|
||||
if timeout > 0:
|
||||
time.sleep(timeout)
|
||||
return True, {}
|
||||
else:
|
||||
# Update reg value
|
||||
self.port_dict = currernt_port_dict
|
||||
return True, self.port_dict
|
||||
print ("get_transceiver_change_event: Should not reach here.")
|
||||
return False, {}
|
@ -0,0 +1,3 @@
|
||||
{
|
||||
"skip_ledd": true
|
||||
}
|
21
device/ragile/x86_64-ragile_ra-b6510-32c-r0/sensors.conf
Normal file
21
device/ragile/x86_64-ragile_ra-b6510-32c-r0/sensors.conf
Normal file
@ -0,0 +1,21 @@
|
||||
# libsensors configuration file
|
||||
# ----------------------------------------------
|
||||
#
|
||||
|
||||
bus "i2c-2" "i2c-0-mux (chan_id 0)"
|
||||
|
||||
chip "lm75-i2c-2-48"
|
||||
label temp1 "LM75_0 air_inlet"
|
||||
set temp1_max 80
|
||||
set temp1_max_hyst 75
|
||||
|
||||
chip "lm75-i2c-2-49"
|
||||
label temp1 "LM75_1 air_outlet"
|
||||
set temp1_max 80
|
||||
set temp1_max_hyst 75
|
||||
|
||||
chip "lm75-i2c-2-4a"
|
||||
label temp1 "LM75_2 hottest"
|
||||
set temp1_max 80
|
||||
set temp1_max_hyst 75
|
||||
|
43
device/ragile/x86_64-ragile_ra-b6510-32c-r0/systest.py
Normal file
43
device/ragile/x86_64-ragile_ra-b6510-32c-r0/systest.py
Normal file
@ -0,0 +1,43 @@
|
||||
#!/usr/bin/python
|
||||
# -*- coding: UTF-8 -*-
|
||||
|
||||
# * onboard interval check
|
||||
# * FAN trays
|
||||
# * PSU
|
||||
# * temp
|
||||
import time
|
||||
import datetime
|
||||
from monitor import status
|
||||
|
||||
def doWork():
|
||||
a=[];
|
||||
'''
|
||||
return: [{'status': '1', 'hw_version': '1.00', 'errcode': 0, 'fan_type': 'M6510-FAN-F', 'errmsg': 'OK', 'Speed': '9778', 'id': 'fan1', 'present': '0', 'sn': '1000000000014'},
|
||||
{'id': 'fan2', 'errmsg': 'not present', 'errcode': -1},
|
||||
{'id': 'fan3', 'errmsg': 'not present', 'errcode': -1},
|
||||
{'id': 'fan4', 'errmsg': 'not present', 'errcode': -1}
|
||||
]
|
||||
description: 1.get id
|
||||
2.errcode equal 0 : dev normal
|
||||
not equal 0 : get errmsg
|
||||
3.other message add when all check success
|
||||
'''
|
||||
status.checkFan(a)
|
||||
#status.getTemp(a)
|
||||
#status.getPsu(a)
|
||||
|
||||
nowTime=datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
|
||||
print nowTime
|
||||
print a
|
||||
def run(interval):
|
||||
while True:
|
||||
try:
|
||||
time_remaining = interval - time.time()%interval
|
||||
time.sleep(time_remaining)
|
||||
doWork()
|
||||
except Exception as e:
|
||||
print(e)
|
||||
|
||||
if __name__ == '__main__':
|
||||
interval = 1
|
||||
run(interval)
|
@ -0,0 +1,129 @@
|
||||
# name lanes alias index speed
|
||||
Ethernet1 65,66 hundredGigE0/1 0 100000
|
||||
Ethernet2 67,68 hundredGigE0/2 1 100000
|
||||
Ethernet3 69,70 hundredGigE0/3 2 100000
|
||||
Ethernet4 71,72 hundredGigE0/4 3 100000
|
||||
Ethernet5 81,82 hundredGigE0/5 4 100000
|
||||
Ethernet6 83,84 hundredGigE0/6 5 100000
|
||||
Ethernet7 85,86 hundredGigE0/7 6 100000
|
||||
Ethernet8 87,88 hundredGigE0/8 7 100000
|
||||
Ethernet9 97,98 hundredGigE0/9 8 100000
|
||||
Ethernet10 99,100 hundredGigE0/10 9 100000
|
||||
Ethernet11 101,102 hundredGigE0/11 10 100000
|
||||
Ethernet12 103,104 hundredGigE0/12 11 100000
|
||||
Ethernet13 113,114 hundredGigE0/13 12 100000
|
||||
Ethernet14 115,116 hundredGigE0/14 13 100000
|
||||
Ethernet15 117,118 hundredGigE0/15 14 100000
|
||||
Ethernet16 119,120 hundredGigE0/16 15 100000
|
||||
Ethernet17 137,138 hundredGigE0/17 16 100000
|
||||
Ethernet18 139,140 hundredGigE0/18 17 100000
|
||||
Ethernet19 141,142 hundredGigE0/19 18 100000
|
||||
Ethernet20 143,144 hundredGigE0/20 19 100000
|
||||
Ethernet21 153,154 hundredGigE0/21 20 100000
|
||||
Ethernet22 155,156 hundredGigE0/22 21 100000
|
||||
Ethernet23 157,158 hundredGigE0/23 22 100000
|
||||
Ethernet24 159,160 hundredGigE0/24 23 100000
|
||||
Ethernet25 169,170 hundredGigE0/25 24 100000
|
||||
Ethernet26 171,172 hundredGigE0/26 25 100000
|
||||
Ethernet27 173,174 hundredGigE0/27 26 100000
|
||||
Ethernet28 175,176 hundredGigE0/28 27 100000
|
||||
Ethernet29 185,186 hundredGigE0/29 28 100000
|
||||
Ethernet30 187,188 hundredGigE0/30 29 100000
|
||||
Ethernet31 189,190 hundredGigE0/31 30 100000
|
||||
Ethernet32 191,192 hundredGigE0/32 31 100000
|
||||
Ethernet33 73,74 hundredGigE0/33 32 100000
|
||||
Ethernet34 75,76 hundredGigE0/34 33 100000
|
||||
Ethernet35 77,78 hundredGigE0/35 34 100000
|
||||
Ethernet36 79,80 hundredGigE0/36 35 100000
|
||||
Ethernet37 89,90 hundredGigE0/37 36 100000
|
||||
Ethernet38 91,92 hundredGigE0/38 37 100000
|
||||
Ethernet39 93,94 hundredGigE0/39 38 100000
|
||||
Ethernet40 95,96 hundredGigE0/40 39 100000
|
||||
Ethernet41 105,106 hundredGigE0/41 40 100000
|
||||
Ethernet42 107,108 hundredGigE0/42 41 100000
|
||||
Ethernet43 109,110 hundredGigE0/43 42 100000
|
||||
Ethernet44 111,112 hundredGigE0/44 43 100000
|
||||
Ethernet45 121,122 hundredGigE0/45 44 100000
|
||||
Ethernet46 123,124 hundredGigE0/46 45 100000
|
||||
Ethernet47 125,126 hundredGigE0/47 46 100000
|
||||
Ethernet48 127,128 hundredGigE0/48 47 100000
|
||||
Ethernet49 129,130 hundredGigE0/49 48 100000
|
||||
Ethernet50 131,132 hundredGigE0/50 49 100000
|
||||
Ethernet51 133,134 hundredGigE0/51 50 100000
|
||||
Ethernet52 135,136 hundredGigE0/52 51 100000
|
||||
Ethernet53 145,146 hundredGigE0/53 52 100000
|
||||
Ethernet54 147,148 hundredGigE0/54 53 100000
|
||||
Ethernet55 149,150 hundredGigE0/55 54 100000
|
||||
Ethernet56 151,152 hundredGigE0/56 55 100000
|
||||
Ethernet57 161,162 hundredGigE0/57 56 100000
|
||||
Ethernet58 163,164 hundredGigE0/58 57 100000
|
||||
Ethernet59 165,166 hundredGigE0/59 58 100000
|
||||
Ethernet60 167,168 hundredGigE0/60 59 100000
|
||||
Ethernet61 177,178 hundredGigE0/61 60 100000
|
||||
Ethernet62 179,180 hundredGigE0/62 61 100000
|
||||
Ethernet63 181,182 hundredGigE0/63 62 100000
|
||||
Ethernet64 183,184 hundredGigE0/64 63 100000
|
||||
Ethernet65 9,10 hundredGigE0/65 64 100000
|
||||
Ethernet66 11,12 hundredGigE0/66 65 100000
|
||||
Ethernet67 13,14 hundredGigE0/67 66 100000
|
||||
Ethernet68 15,16 hundredGigE0/68 67 100000
|
||||
Ethernet69 25,26 hundredGigE0/69 68 100000
|
||||
Ethernet70 27,28 hundredGigE0/70 69 100000
|
||||
Ethernet71 29,30 hundredGigE0/71 70 100000
|
||||
Ethernet72 31,32 hundredGigE0/72 71 100000
|
||||
Ethernet73 41,42 hundredGigE0/73 72 100000
|
||||
Ethernet74 43,44 hundredGigE0/74 73 100000
|
||||
Ethernet75 45,46 hundredGigE0/75 74 100000
|
||||
Ethernet76 47,48 hundredGigE0/76 75 100000
|
||||
Ethernet77 57,58 hundredGigE0/77 76 100000
|
||||
Ethernet78 59,60 hundredGigE0/78 77 100000
|
||||
Ethernet79 61,62 hundredGigE0/79 78 100000
|
||||
Ethernet80 63,64 hundredGigE0/80 79 100000
|
||||
Ethernet81 193,194 hundredGigE0/81 80 100000
|
||||
Ethernet82 195,196 hundredGigE0/82 81 100000
|
||||
Ethernet83 197,198 hundredGigE0/83 82 100000
|
||||
Ethernet84 199,200 hundredGigE0/84 83 100000
|
||||
Ethernet85 209,210 hundredGigE0/85 84 100000
|
||||
Ethernet86 211,212 hundredGigE0/86 85 100000
|
||||
Ethernet87 213,214 hundredGigE0/87 86 100000
|
||||
Ethernet88 215,216 hundredGigE0/88 87 100000
|
||||
Ethernet89 225,226 hundredGigE0/89 88 100000
|
||||
Ethernet90 227,228 hundredGigE0/90 89 100000
|
||||
Ethernet91 229,230 hundredGigE0/91 90 100000
|
||||
Ethernet92 231,232 hundredGigE0/92 91 100000
|
||||
Ethernet93 241,242 hundredGigE0/93 92 100000
|
||||
Ethernet94 243,244 hundredGigE0/94 93 100000
|
||||
Ethernet95 245,246 hundredGigE0/95 94 100000
|
||||
Ethernet96 247,248 hundredGigE0/96 95 100000
|
||||
Ethernet97 1,2 hundredGigE0/97 96 100000
|
||||
Ethernet98 3,4 hundredGigE0/98 97 100000
|
||||
Ethernet99 5,6 hundredGigE0/99 98 100000
|
||||
Ethernet100 7,8 hundredGigE0/100 99 100000
|
||||
Ethernet101 17,18 hundredGigE0/101 100 100000
|
||||
Ethernet102 19,20 hundredGigE0/102 101 100000
|
||||
Ethernet103 21,22 hundredGigE0/103 102 100000
|
||||
Ethernet104 23,24 hundredGigE0/104 103 100000
|
||||
Ethernet105 33,34 hundredGigE0/105 104 100000
|
||||
Ethernet106 35,36 hundredGigE0/106 105 100000
|
||||
Ethernet107 37,38 hundredGigE0/107 106 100000
|
||||
Ethernet108 39,40 hundredGigE0/108 107 100000
|
||||
Ethernet109 49,50 hundredGigE0/109 108 100000
|
||||
Ethernet110 51,52 hundredGigE0/110 109 100000
|
||||
Ethernet111 53,54 hundredGigE0/111 110 100000
|
||||
Ethernet112 55,56 hundredGigE0/112 111 100000
|
||||
Ethernet113 201,202 hundredGigE0/113 112 100000
|
||||
Ethernet114 203,204 hundredGigE0/114 113 100000
|
||||
Ethernet115 205,206 hundredGigE0/115 114 100000
|
||||
Ethernet116 207,208 hundredGigE0/116 115 100000
|
||||
Ethernet117 217,218 hundredGigE0/117 116 100000
|
||||
Ethernet118 219,220 hundredGigE0/118 117 100000
|
||||
Ethernet119 221,222 hundredGigE0/119 118 100000
|
||||
Ethernet120 223,224 hundredGigE0/120 119 100000
|
||||
Ethernet121 233,234 hundredGigE0/121 120 100000
|
||||
Ethernet122 235,236 hundredGigE0/122 121 100000
|
||||
Ethernet123 237,238 hundredGigE0/123 122 100000
|
||||
Ethernet124 239,240 hundredGigE0/124 123 100000
|
||||
Ethernet125 249,250 hundredGigE0/125 124 100000
|
||||
Ethernet126 251,252 hundredGigE0/126 125 100000
|
||||
Ethernet127 253,254 hundredGigE0/127 126 100000
|
||||
Ethernet128 255,256 hundredGigE0/128 127 100000
|
@ -0,0 +1 @@
|
||||
SAI_INIT_CONFIG_FILE=/usr/share/sonic/hwsku/th3-ra-b6920-4s-128x100G.config.bcm
|
@ -0,0 +1,708 @@
|
||||
#This is for a 4slot* 32*100G configuration PAM4 mode (2 lanes per 100G)
|
||||
#rate_ext_mdio_divisor=100
|
||||
port_init_cl72=0
|
||||
port_init_autoneg=0
|
||||
pcie_file=/usr/share/sonic/platform/pcie.cint
|
||||
capi_level=1
|
||||
port_fec=3
|
||||
phy_gearbox_enable.0=1
|
||||
phy_pin_compatibility_enable.0=0
|
||||
cfg_int_phy_ctrl.0=1
|
||||
mmu_port_num_mc_queue=2
|
||||
bcm_tunnel_term_compatible_mode=1
|
||||
pbmp_xport_xe.0=0x8ffff8ffffcffff8ffff8ffff8ffffcffff9fffe
|
||||
#serdes_tx_taps_ce=pam4:0:140:0:0:0:0
|
||||
ccm_dma_enable=0
|
||||
ccmdma_intr_enable=0
|
||||
ctr_evict_enable=0
|
||||
mem_cache_enable=0
|
||||
parity_correction=0
|
||||
parity_enable=0
|
||||
phy_enable=1
|
||||
phy_null=1
|
||||
fpem_mem_entries=65536
|
||||
pll_bypass=1
|
||||
init_all_modules=0
|
||||
l3_mem_entries=16384
|
||||
l3_alpm_enable=2
|
||||
ipv6_lpm_128b_enable=0x1
|
||||
l3_max_ecmp_mode=1
|
||||
|
||||
stand_alone_phy_init=1
|
||||
port_phy_addr_1.0=0x220
|
||||
port_phy_addr_2.0=0x220
|
||||
port_phy_addr_3.0=0x220
|
||||
port_phy_addr_4.0=0x220
|
||||
port_phy_addr_13.0=0x224
|
||||
port_phy_addr_14.0=0x224
|
||||
port_phy_addr_15.0=0x224
|
||||
port_phy_addr_16.0=0x224
|
||||
port_phy_addr_20.0=0x248
|
||||
port_phy_addr_21.0=0x248
|
||||
port_phy_addr_22.0=0x248
|
||||
port_phy_addr_23.0=0x248
|
||||
port_phy_addr_32.0=0x22c
|
||||
port_phy_addr_33.0=0x22c
|
||||
port_phy_addr_34.0=0x22c
|
||||
port_phy_addr_35.0=0x22c
|
||||
port_phy_addr_124.0=0x250
|
||||
port_phy_addr_125.0=0x250
|
||||
port_phy_addr_126.0=0x250
|
||||
port_phy_addr_127.0=0x250
|
||||
port_phy_addr_128.0=0x254
|
||||
port_phy_addr_129.0=0x254
|
||||
port_phy_addr_130.0=0x254
|
||||
port_phy_addr_131.0=0x254
|
||||
port_phy_addr_144.0=0x278
|
||||
port_phy_addr_145.0=0x278
|
||||
port_phy_addr_146.0=0x278
|
||||
port_phy_addr_147.0=0x278
|
||||
port_phy_addr_148.0=0x27c
|
||||
port_phy_addr_149.0=0x27c
|
||||
port_phy_addr_150.0=0x27c
|
||||
port_phy_addr_151.0=0x27c
|
||||
port_phy_addr_5.0=0x140
|
||||
port_phy_addr_6.0=0x140
|
||||
port_phy_addr_7.0=0x140
|
||||
port_phy_addr_8.0=0x140
|
||||
port_phy_addr_9.0=0x144
|
||||
port_phy_addr_10.0=0x144
|
||||
port_phy_addr_11.0=0x144
|
||||
port_phy_addr_12.0=0x144
|
||||
port_phy_addr_24.0=0x168
|
||||
port_phy_addr_25.0=0x168
|
||||
port_phy_addr_26.0=0x168
|
||||
port_phy_addr_27.0=0x168
|
||||
port_phy_addr_28.0=0x14c
|
||||
port_phy_addr_29.0=0x14c
|
||||
port_phy_addr_30.0=0x14c
|
||||
port_phy_addr_31.0=0x14c
|
||||
port_phy_addr_120.0=0x170
|
||||
port_phy_addr_121.0=0x170
|
||||
port_phy_addr_122.0=0x170
|
||||
port_phy_addr_123.0=0x170
|
||||
port_phy_addr_132.0=0x174
|
||||
port_phy_addr_133.0=0x174
|
||||
port_phy_addr_134.0=0x174
|
||||
port_phy_addr_135.0=0x174
|
||||
port_phy_addr_140.0=0x218
|
||||
port_phy_addr_141.0=0x218
|
||||
port_phy_addr_142.0=0x218
|
||||
port_phy_addr_143.0=0x218
|
||||
port_phy_addr_152.0=0x21c
|
||||
port_phy_addr_153.0=0x21c
|
||||
port_phy_addr_154.0=0x21c
|
||||
port_phy_addr_155.0=0x21c
|
||||
port_phy_addr_44.0=0x60
|
||||
port_phy_addr_45.0=0x60
|
||||
port_phy_addr_46.0=0x60
|
||||
port_phy_addr_47.0=0x60
|
||||
port_phy_addr_52.0=0x64
|
||||
port_phy_addr_53.0=0x64
|
||||
port_phy_addr_54.0=0x64
|
||||
port_phy_addr_55.0=0x64
|
||||
port_phy_addr_64.0=0x108
|
||||
port_phy_addr_65.0=0x108
|
||||
port_phy_addr_66.0=0x108
|
||||
port_phy_addr_67.0=0x108
|
||||
port_phy_addr_72.0=0x6c
|
||||
port_phy_addr_73.0=0x6c
|
||||
port_phy_addr_74.0=0x6c
|
||||
port_phy_addr_75.0=0x6c
|
||||
port_phy_addr_80.0=0x110
|
||||
port_phy_addr_81.0=0x110
|
||||
port_phy_addr_82.0=0x110
|
||||
port_phy_addr_83.0=0x110
|
||||
port_phy_addr_88.0=0x114
|
||||
port_phy_addr_89.0=0x114
|
||||
port_phy_addr_90.0=0x114
|
||||
port_phy_addr_91.0=0x114
|
||||
port_phy_addr_100.0=0x138
|
||||
port_phy_addr_101.0=0x138
|
||||
port_phy_addr_102.0=0x138
|
||||
port_phy_addr_103.0=0x138
|
||||
port_phy_addr_108.0=0x13c
|
||||
port_phy_addr_109.0=0x13c
|
||||
port_phy_addr_110.0=0x13c
|
||||
port_phy_addr_111.0=0x13c
|
||||
port_phy_addr_40.0=0x0
|
||||
port_phy_addr_41.0=0x0
|
||||
port_phy_addr_42.0=0x0
|
||||
port_phy_addr_43.0=0x0
|
||||
port_phy_addr_48.0=0x4
|
||||
port_phy_addr_49.0=0x4
|
||||
port_phy_addr_50.0=0x4
|
||||
port_phy_addr_51.0=0x4
|
||||
port_phy_addr_60.0=0x28
|
||||
port_phy_addr_61.0=0x28
|
||||
port_phy_addr_62.0=0x28
|
||||
port_phy_addr_63.0=0x28
|
||||
port_phy_addr_68.0=0xc
|
||||
port_phy_addr_69.0=0xc
|
||||
port_phy_addr_70.0=0xc
|
||||
port_phy_addr_71.0=0xc
|
||||
port_phy_addr_84.0=0x30
|
||||
port_phy_addr_85.0=0x30
|
||||
port_phy_addr_86.0=0x30
|
||||
port_phy_addr_87.0=0x30
|
||||
port_phy_addr_92.0=0x34
|
||||
port_phy_addr_93.0=0x34
|
||||
port_phy_addr_94.0=0x34
|
||||
port_phy_addr_95.0=0x34
|
||||
port_phy_addr_104.0=0x58
|
||||
port_phy_addr_105.0=0x58
|
||||
port_phy_addr_106.0=0x58
|
||||
port_phy_addr_107.0=0x58
|
||||
port_phy_addr_112.0=0x5c
|
||||
port_phy_addr_113.0=0x5c
|
||||
port_phy_addr_114.0=0x5c
|
||||
port_phy_addr_115.0=0x5c
|
||||
|
||||
sap_rx_polarity_flip_1.0=0x2000
|
||||
sap_rx_polarity_flip_13.0=0x2000
|
||||
sap_rx_polarity_flip_20.0=0x2000
|
||||
sap_rx_polarity_flip_32.0=0x2000
|
||||
sap_rx_polarity_flip_124.0=0x2000
|
||||
sap_rx_polarity_flip_128.0=0x2000
|
||||
sap_rx_polarity_flip_144.0=0x2000
|
||||
sap_rx_polarity_flip_148.0=0x2000
|
||||
sap_rx_polarity_flip_5.0=0x2000
|
||||
sap_rx_polarity_flip_9.0=0x2000
|
||||
sap_rx_polarity_flip_24.0=0x2000
|
||||
sap_rx_polarity_flip_28.0=0x2000
|
||||
sap_rx_polarity_flip_120.0=0x2000
|
||||
sap_rx_polarity_flip_132.0=0x2000
|
||||
sap_rx_polarity_flip_140.0=0x2000
|
||||
sap_rx_polarity_flip_152.0=0x2000
|
||||
sap_rx_polarity_flip_44.0=0x2000
|
||||
sap_rx_polarity_flip_52.0=0x2000
|
||||
sap_rx_polarity_flip_64.0=0x2000
|
||||
sap_rx_polarity_flip_72.0=0x2000
|
||||
sap_rx_polarity_flip_80.0=0x2000
|
||||
sap_rx_polarity_flip_88.0=0x2000
|
||||
sap_rx_polarity_flip_100.0=0x2000
|
||||
sap_rx_polarity_flip_108.0=0x2000
|
||||
sap_rx_polarity_flip_40.0=0x2000
|
||||
sap_rx_polarity_flip_48.0=0x2000
|
||||
sap_rx_polarity_flip_60.0=0x2000
|
||||
sap_rx_polarity_flip_68.0=0x2000
|
||||
sap_rx_polarity_flip_84.0=0x2000
|
||||
sap_rx_polarity_flip_92.0=0x2000
|
||||
sap_rx_polarity_flip_104.0=0x2000
|
||||
sap_rx_polarity_flip_112.0=0x2000
|
||||
|
||||
sap_tx_polarity_flip_1.0=0x8414
|
||||
sap_tx_polarity_flip_13.0=0x8414
|
||||
sap_tx_polarity_flip_20.0=0x8414
|
||||
sap_tx_polarity_flip_32.0=0x8414
|
||||
sap_tx_polarity_flip_124.0=0x8414
|
||||
sap_tx_polarity_flip_128.0=0x8414
|
||||
sap_tx_polarity_flip_144.0=0x8414
|
||||
sap_tx_polarity_flip_148.0=0x8414
|
||||
sap_tx_polarity_flip_5.0=0x8414
|
||||
sap_tx_polarity_flip_9.0=0x8414
|
||||
sap_tx_polarity_flip_24.0=0x8414
|
||||
sap_tx_polarity_flip_28.0=0x8414
|
||||
sap_tx_polarity_flip_120.0=0x8414
|
||||
sap_tx_polarity_flip_132.0=0x8414
|
||||
sap_tx_polarity_flip_140.0=0x8414
|
||||
sap_tx_polarity_flip_152.0=0x8414
|
||||
sap_tx_polarity_flip_44.0=0x8414
|
||||
sap_tx_polarity_flip_52.0=0x8414
|
||||
sap_tx_polarity_flip_64.0=0x8414
|
||||
sap_tx_polarity_flip_72.0=0x8414
|
||||
sap_tx_polarity_flip_80.0=0x8414
|
||||
sap_tx_polarity_flip_88.0=0x8414
|
||||
sap_tx_polarity_flip_100.0=0x8414
|
||||
sap_tx_polarity_flip_108.0=0x8414
|
||||
sap_tx_polarity_flip_40.0=0x8414
|
||||
sap_tx_polarity_flip_48.0=0x8414
|
||||
sap_tx_polarity_flip_60.0=0x8414
|
||||
sap_tx_polarity_flip_68.0=0x8414
|
||||
sap_tx_polarity_flip_84.0=0x8414
|
||||
sap_tx_polarity_flip_92.0=0x8414
|
||||
sap_tx_polarity_flip_104.0=0x8414
|
||||
sap_tx_polarity_flip_112.0=0x8414
|
||||
|
||||
sap_mdio_num_1.0=9
|
||||
sap_mdio_num_13.0=9
|
||||
sap_mdio_num_20.0=10
|
||||
sap_mdio_num_32.0=9
|
||||
sap_mdio_num_124.0=10
|
||||
sap_mdio_num_128.0=10
|
||||
sap_mdio_num_144.0=11
|
||||
sap_mdio_num_148.0=11
|
||||
sap_mdio_num_5.0=6
|
||||
sap_mdio_num_9.0=6
|
||||
sap_mdio_num_24.0=7
|
||||
sap_mdio_num_28.0=6
|
||||
sap_mdio_num_120.0=7
|
||||
sap_mdio_num_132.0=7
|
||||
sap_mdio_num_140.0=8
|
||||
sap_mdio_num_152.0=8
|
||||
sap_mdio_num_44.0=3
|
||||
sap_mdio_num_52.0=3
|
||||
sap_mdio_num_64.0=4
|
||||
sap_mdio_num_72.0=3
|
||||
sap_mdio_num_80.0=4
|
||||
sap_mdio_num_88.0=4
|
||||
sap_mdio_num_100.0=5
|
||||
sap_mdio_num_108.0=5
|
||||
sap_mdio_num_40.0=0
|
||||
sap_mdio_num_48.0=0
|
||||
sap_mdio_num_60.0=1
|
||||
sap_mdio_num_68.0=0
|
||||
sap_mdio_num_84.0=1
|
||||
sap_mdio_num_92.0=1
|
||||
sap_mdio_num_104.0=2
|
||||
sap_mdio_num_112.0=2
|
||||
|
||||
#slot 1 bc 8 10 12 14
|
||||
portmap_40=65:100
|
||||
portmap_41=67:100
|
||||
portmap_42=69:100
|
||||
portmap_43=71:100
|
||||
|
||||
portmap_48=81:100
|
||||
portmap_49=83:100
|
||||
portmap_50=85:100
|
||||
portmap_51=87:100
|
||||
|
||||
portmap_60=97:100
|
||||
portmap_61=99:100
|
||||
portmap_62=101:100
|
||||
portmap_63=103:100
|
||||
|
||||
portmap_68=113:100
|
||||
portmap_69=115:100
|
||||
portmap_70=117:100
|
||||
portmap_71=119:100
|
||||
|
||||
#slot 1 bc 17 19 21 23
|
||||
|
||||
portmap_84=137:100
|
||||
portmap_85=139:100
|
||||
portmap_86=141:100
|
||||
portmap_87=143:100
|
||||
|
||||
portmap_92=153:100
|
||||
portmap_93=155:100
|
||||
portmap_94=157:100
|
||||
portmap_95=159:100
|
||||
|
||||
portmap_104=169:100
|
||||
portmap_105=171:100
|
||||
portmap_106=173:100
|
||||
portmap_107=175:100
|
||||
|
||||
portmap_112=185:100
|
||||
portmap_113=187:100
|
||||
portmap_114=189:100
|
||||
portmap_115=191:100
|
||||
|
||||
phy_chain_rx_lane_map_physical{65.0}=0x37046215
|
||||
phy_chain_tx_lane_map_physical{65.0}=0x75140623
|
||||
phy_chain_rx_lane_map_physical{81.0}=0x64301572
|
||||
phy_chain_tx_lane_map_physical{81.0}=0x52160374
|
||||
phy_chain_rx_lane_map_physical{97.0}=0x21537406
|
||||
phy_chain_tx_lane_map_physical{97.0}=0x62137450
|
||||
phy_chain_rx_lane_map_physical{113.0}=0x26107543
|
||||
phy_chain_tx_lane_map_physical{113.0}=0x61023754
|
||||
phy_chain_rx_lane_map_physical{137.0}=0x62130457
|
||||
phy_chain_tx_lane_map_physical{137.0}=0x15230746
|
||||
phy_chain_rx_lane_map_physical{153.0}=0x60157432
|
||||
phy_chain_tx_lane_map_physical{153.0}=0x34012576
|
||||
phy_chain_rx_lane_map_physical{169.0}=0x53026714
|
||||
phy_chain_tx_lane_map_physical{169.0}=0x34612057
|
||||
phy_chain_rx_lane_map_physical{185.0}=0x72456103
|
||||
phy_chain_tx_lane_map_physical{185.0}=0x25413076
|
||||
|
||||
serdes_core_rx_polarity_flip_physical{65}=0x48
|
||||
serdes_core_tx_polarity_flip_physical{65}=0xb1
|
||||
serdes_core_rx_polarity_flip_physical{81}=0x81
|
||||
serdes_core_tx_polarity_flip_physical{81}=0x2f
|
||||
serdes_core_rx_polarity_flip_physical{97}=0x9c
|
||||
serdes_core_tx_polarity_flip_physical{97}=0x02
|
||||
serdes_core_rx_polarity_flip_physical{113}=0xaf
|
||||
serdes_core_tx_polarity_flip_physical{113}=0xd2
|
||||
serdes_core_rx_polarity_flip_physical{137}=0x2b
|
||||
serdes_core_tx_polarity_flip_physical{137}=0x26
|
||||
serdes_core_rx_polarity_flip_physical{153}=0x0a
|
||||
serdes_core_tx_polarity_flip_physical{153}=0xb0
|
||||
serdes_core_rx_polarity_flip_physical{169}=0x0d
|
||||
serdes_core_tx_polarity_flip_physical{169}=0x3e
|
||||
serdes_core_rx_polarity_flip_physical{185}=0xa2
|
||||
serdes_core_tx_polarity_flip_physical{185}=0x36
|
||||
|
||||
#slot 2 bc 9 11 13 15
|
||||
portmap_44=73:100
|
||||
portmap_45=75:100
|
||||
portmap_46=77:100
|
||||
portmap_47=79:100
|
||||
|
||||
portmap_52=89:100
|
||||
portmap_53=91:100
|
||||
portmap_54=93:100
|
||||
portmap_55=95:100
|
||||
|
||||
portmap_64=105:100
|
||||
portmap_65=107:100
|
||||
portmap_66=109:100
|
||||
portmap_67=111:100
|
||||
|
||||
portmap_72=121:100
|
||||
portmap_73=123:100
|
||||
portmap_74=125:100
|
||||
portmap_75=127:100
|
||||
|
||||
#bc 16 18 20 22
|
||||
|
||||
portmap_80=129:100
|
||||
portmap_81=131:100
|
||||
portmap_82=133:100
|
||||
portmap_83=135:100
|
||||
|
||||
portmap_88=145:100
|
||||
portmap_89=147:100
|
||||
portmap_90=149:100
|
||||
portmap_91=151:100
|
||||
|
||||
portmap_100=161:100
|
||||
portmap_101=163:100
|
||||
portmap_102=165:100
|
||||
portmap_103=167:100
|
||||
|
||||
portmap_108=177:100
|
||||
portmap_109=179:100
|
||||
portmap_110=181:100
|
||||
portmap_111=183:100
|
||||
|
||||
phy_chain_rx_lane_map_physical{73.0}=0x23760415
|
||||
phy_chain_tx_lane_map_physical{73.0}=0x31057624
|
||||
phy_chain_rx_lane_map_physical{89.0}=0x13204756
|
||||
phy_chain_tx_lane_map_physical{89.0}=0x31056724
|
||||
phy_chain_rx_lane_map_physical{105.0}=0x62375401
|
||||
phy_chain_tx_lane_map_physical{105.0}=0x54762310
|
||||
phy_chain_rx_lane_map_physical{121.0}=0x32107546
|
||||
phy_chain_tx_lane_map_physical{121.0}=0x67215340
|
||||
phy_chain_rx_lane_map_physical{129.0}=0x01236745
|
||||
phy_chain_tx_lane_map_physical{129.0}=0x65347012
|
||||
phy_chain_rx_lane_map_physical{145.0}=0x65723401
|
||||
phy_chain_tx_lane_map_physical{145.0}=0x47650132
|
||||
phy_chain_rx_lane_map_physical{161.0}=0x74532601
|
||||
phy_chain_tx_lane_map_physical{161.0}=0x67421350
|
||||
phy_chain_rx_lane_map_physical{177.0}=0x07516342
|
||||
phy_chain_tx_lane_map_physical{177.0}=0x67403152
|
||||
|
||||
serdes_core_rx_polarity_flip_physical{73}=0xb6
|
||||
serdes_core_tx_polarity_flip_physical{73}=0x25
|
||||
serdes_core_rx_polarity_flip_physical{89}=0x73
|
||||
serdes_core_tx_polarity_flip_physical{89}=0x27
|
||||
serdes_core_rx_polarity_flip_physical{105}=0x88
|
||||
serdes_core_tx_polarity_flip_physical{105}=0x9a
|
||||
serdes_core_rx_polarity_flip_physical{121}=0xfa
|
||||
serdes_core_tx_polarity_flip_physical{121}=0xe3
|
||||
serdes_core_rx_polarity_flip_physical{129}=0xf5
|
||||
serdes_core_tx_polarity_flip_physical{129}=0xe6
|
||||
serdes_core_rx_polarity_flip_physical{145}=0x3e
|
||||
serdes_core_tx_polarity_flip_physical{145}=0x96
|
||||
serdes_core_rx_polarity_flip_physical{161}=0x0b
|
||||
serdes_core_tx_polarity_flip_physical{161}=0x7a
|
||||
serdes_core_rx_polarity_flip_physical{177}=0x8d
|
||||
serdes_core_tx_polarity_flip_physical{177}=0x5a
|
||||
|
||||
#slot 3
|
||||
#bc 1 3 5 7
|
||||
|
||||
portmap_5=9:100
|
||||
portmap_6=11:100
|
||||
portmap_7=13:100
|
||||
portmap_8=15:100
|
||||
|
||||
portmap_9=25:100
|
||||
portmap_10=27:100
|
||||
portmap_11=29:100
|
||||
portmap_12=31:100
|
||||
|
||||
portmap_24=41:100
|
||||
portmap_25=43:100
|
||||
portmap_26=45:100
|
||||
portmap_27=47:100
|
||||
|
||||
portmap_28=57:100
|
||||
portmap_29=59:100
|
||||
portmap_30=61:100
|
||||
portmap_31=63:100
|
||||
|
||||
#bc 24 26 28 30
|
||||
portmap_120=193:100
|
||||
portmap_121=195:100
|
||||
portmap_122=197:100
|
||||
portmap_123=199:100
|
||||
|
||||
portmap_132=209:100
|
||||
portmap_133=211:100
|
||||
portmap_134=213:100
|
||||
portmap_135=215:100
|
||||
|
||||
portmap_140=225:100
|
||||
portmap_141=227:100
|
||||
portmap_142=229:100
|
||||
portmap_143=231:100
|
||||
|
||||
portmap_152=241:100
|
||||
portmap_153=243:100
|
||||
portmap_154=245:100
|
||||
portmap_155=247:100
|
||||
|
||||
phy_chain_rx_lane_map_physical{9.0}=0x20541673
|
||||
phy_chain_tx_lane_map_physical{9.0}=0x32546107
|
||||
phy_chain_rx_lane_map_physical{25.0}=0x32104756
|
||||
phy_chain_tx_lane_map_physical{25.0}=0x30214756
|
||||
phy_chain_rx_lane_map_physical{41.0}=0x23610457
|
||||
phy_chain_tx_lane_map_physical{41.0}=0x57463201
|
||||
phy_chain_rx_lane_map_physical{57.0}=0x35671042
|
||||
phy_chain_tx_lane_map_physical{57.0}=0x47026351
|
||||
phy_chain_rx_lane_map_physical{193.0}=0x46712503
|
||||
phy_chain_tx_lane_map_physical{193.0}=0x57063241
|
||||
phy_chain_rx_lane_map_physical{209.0}=0x54302761
|
||||
phy_chain_tx_lane_map_physical{209.0}=0x50674312
|
||||
phy_chain_rx_lane_map_physical{225.0}=0x54762310
|
||||
phy_chain_tx_lane_map_physical{225.0}=0x65042371
|
||||
phy_chain_rx_lane_map_physical{241.0}=0x51026473
|
||||
phy_chain_tx_lane_map_physical{241.0}=0x40167532
|
||||
|
||||
serdes_core_rx_polarity_flip_physical{9}=0xac
|
||||
serdes_core_tx_polarity_flip_physical{9}=0xfc
|
||||
serdes_core_rx_polarity_flip_physical{25}=0xf7
|
||||
serdes_core_tx_polarity_flip_physical{25}=0x39
|
||||
serdes_core_rx_polarity_flip_physical{41}=0xd3
|
||||
serdes_core_tx_polarity_flip_physical{41}=0xb6
|
||||
serdes_core_rx_polarity_flip_physical{57}=0xad
|
||||
serdes_core_tx_polarity_flip_physical{57}=0x61
|
||||
serdes_core_rx_polarity_flip_physical{193}=0x74
|
||||
serdes_core_tx_polarity_flip_physical{193}=0xd0
|
||||
serdes_core_rx_polarity_flip_physical{209}=0x9f
|
||||
serdes_core_tx_polarity_flip_physical{209}=0x41
|
||||
serdes_core_rx_polarity_flip_physical{225}=0xfe
|
||||
serdes_core_tx_polarity_flip_physical{225}=0x47
|
||||
serdes_core_rx_polarity_flip_physical{241}=0x5a
|
||||
serdes_core_tx_polarity_flip_physical{241}=0xd9
|
||||
|
||||
#slot 4
|
||||
#bc 0 2 4 6
|
||||
portmap_1=1:100
|
||||
portmap_2=3:100
|
||||
portmap_3=5:100
|
||||
portmap_4=7:100
|
||||
|
||||
portmap_13=17:100
|
||||
portmap_14=19:100
|
||||
portmap_15=21:100
|
||||
portmap_16=23:100
|
||||
|
||||
portmap_20=33:100
|
||||
portmap_21=35:100
|
||||
portmap_22=37:100
|
||||
portmap_23=39:100
|
||||
|
||||
portmap_32=49:100
|
||||
portmap_33=51:100
|
||||
portmap_34=53:100
|
||||
portmap_35=55:100
|
||||
|
||||
#bc 25 27 29 31
|
||||
|
||||
portmap_124=201:100
|
||||
portmap_125=203:100
|
||||
portmap_126=205:100
|
||||
portmap_127=207:100
|
||||
|
||||
portmap_128=217:100
|
||||
portmap_129=219:100
|
||||
portmap_130=221:100
|
||||
portmap_131=223:100
|
||||
|
||||
portmap_144=233:100
|
||||
portmap_145=235:100
|
||||
portmap_146=237:100
|
||||
portmap_147=239:100
|
||||
|
||||
portmap_148=249:100
|
||||
portmap_149=251:100
|
||||
portmap_150=253:100
|
||||
portmap_151=255:100
|
||||
|
||||
phy_chain_rx_lane_map_physical{1.0}=0x62147035
|
||||
phy_chain_tx_lane_map_physical{1.0}=0x35046712
|
||||
phy_chain_rx_lane_map_physical{17.0}=0x76345012
|
||||
phy_chain_tx_lane_map_physical{17.0}=0x45102367
|
||||
phy_chain_rx_lane_map_physical{33.0}=0x12063457
|
||||
phy_chain_tx_lane_map_physical{33.0}=0x23607541
|
||||
phy_chain_rx_lane_map_physical{49.0}=0x03216745
|
||||
phy_chain_tx_lane_map_physical{49.0}=0x14650273
|
||||
phy_chain_rx_lane_map_physical{201.0}=0x34105627
|
||||
phy_chain_tx_lane_map_physical{201.0}=0x12503467
|
||||
phy_chain_rx_lane_map_physical{217.0}=0x02476351
|
||||
phy_chain_tx_lane_map_physical{217.0}=0x31524067
|
||||
phy_chain_rx_lane_map_physical{233.0}=0x10754623
|
||||
phy_chain_tx_lane_map_physical{233.0}=0x02314576
|
||||
phy_chain_rx_lane_map_physical{249.0}=0x34762510
|
||||
phy_chain_tx_lane_map_physical{249.0}=0x40271653
|
||||
|
||||
serdes_core_rx_polarity_flip_physical{1}=0xe0
|
||||
serdes_core_tx_polarity_flip_physical{1}=0xea
|
||||
serdes_core_rx_polarity_flip_physical{17}=0x42
|
||||
serdes_core_tx_polarity_flip_physical{17}=0x8a
|
||||
serdes_core_rx_polarity_flip_physical{33}=0xd1
|
||||
serdes_core_tx_polarity_flip_physical{33}=0x24
|
||||
serdes_core_rx_polarity_flip_physical{49}=0x23
|
||||
serdes_core_tx_polarity_flip_physical{49}=0xac
|
||||
serdes_core_rx_polarity_flip_physical{201}=0xa8
|
||||
serdes_core_tx_polarity_flip_physical{201}=0x13
|
||||
serdes_core_rx_polarity_flip_physical{217}=0xdf
|
||||
serdes_core_tx_polarity_flip_physical{217}=0x48
|
||||
serdes_core_rx_polarity_flip_physical{233}=0xdf
|
||||
serdes_core_tx_polarity_flip_physical{233}=0x84
|
||||
serdes_core_rx_polarity_flip_physical{249}=0xfb
|
||||
serdes_core_tx_polarity_flip_physical{249}=0xdc
|
||||
|
||||
dport_map_port_40=1
|
||||
dport_map_port_41=2
|
||||
dport_map_port_42=3
|
||||
dport_map_port_43=4
|
||||
dport_map_port_48=5
|
||||
dport_map_port_49=6
|
||||
dport_map_port_50=7
|
||||
dport_map_port_51=8
|
||||
dport_map_port_60=9
|
||||
dport_map_port_61=10
|
||||
dport_map_port_62=11
|
||||
dport_map_port_63=12
|
||||
dport_map_port_68=13
|
||||
dport_map_port_69=14
|
||||
dport_map_port_70=15
|
||||
dport_map_port_71=16
|
||||
dport_map_port_84=17
|
||||
dport_map_port_85=18
|
||||
dport_map_port_86=19
|
||||
dport_map_port_87=20
|
||||
dport_map_port_92=21
|
||||
dport_map_port_93=22
|
||||
dport_map_port_94=23
|
||||
dport_map_port_95=24
|
||||
dport_map_port_104=25
|
||||
dport_map_port_105=26
|
||||
dport_map_port_106=27
|
||||
dport_map_port_107=28
|
||||
dport_map_port_112=29
|
||||
dport_map_port_113=30
|
||||
dport_map_port_114=31
|
||||
dport_map_port_115=32
|
||||
|
||||
dport_map_port_44=33
|
||||
dport_map_port_45=34
|
||||
dport_map_port_46=35
|
||||
dport_map_port_47=36
|
||||
dport_map_port_52=37
|
||||
dport_map_port_53=38
|
||||
dport_map_port_54=39
|
||||
dport_map_port_55=40
|
||||
dport_map_port_64=41
|
||||
dport_map_port_65=42
|
||||
dport_map_port_66=43
|
||||
dport_map_port_67=44
|
||||
dport_map_port_72=45
|
||||
dport_map_port_73=46
|
||||
dport_map_port_74=47
|
||||
dport_map_port_75=48
|
||||
dport_map_port_80=49
|
||||
dport_map_port_81=50
|
||||
dport_map_port_82=51
|
||||
dport_map_port_83=52
|
||||
dport_map_port_88=53
|
||||
dport_map_port_89=54
|
||||
dport_map_port_90=55
|
||||
dport_map_port_91=56
|
||||
dport_map_port_100=57
|
||||
dport_map_port_101=58
|
||||
dport_map_port_102=59
|
||||
dport_map_port_103=60
|
||||
dport_map_port_108=61
|
||||
dport_map_port_109=62
|
||||
dport_map_port_110=63
|
||||
dport_map_port_111=64
|
||||
|
||||
dport_map_port_5=65
|
||||
dport_map_port_6=66
|
||||
dport_map_port_7=67
|
||||
dport_map_port_8=68
|
||||
dport_map_port_9=69
|
||||
dport_map_port_10=70
|
||||
dport_map_port_11=71
|
||||
dport_map_port_12=72
|
||||
dport_map_port_24=73
|
||||
dport_map_port_25=74
|
||||
dport_map_port_26=75
|
||||
dport_map_port_27=76
|
||||
dport_map_port_28=77
|
||||
dport_map_port_29=78
|
||||
dport_map_port_30=79
|
||||
dport_map_port_31=80
|
||||
dport_map_port_120=81
|
||||
dport_map_port_121=82
|
||||
dport_map_port_122=83
|
||||
dport_map_port_123=84
|
||||
dport_map_port_132=85
|
||||
dport_map_port_133=86
|
||||
dport_map_port_134=87
|
||||
dport_map_port_135=88
|
||||
dport_map_port_140=89
|
||||
dport_map_port_141=90
|
||||
dport_map_port_142=91
|
||||
dport_map_port_143=92
|
||||
dport_map_port_152=93
|
||||
dport_map_port_153=94
|
||||
dport_map_port_154=95
|
||||
dport_map_port_155=96
|
||||
|
||||
dport_map_port_1=97
|
||||
dport_map_port_2=98
|
||||
dport_map_port_3=99
|
||||
dport_map_port_4=100
|
||||
dport_map_port_13=101
|
||||
dport_map_port_14=102
|
||||
dport_map_port_15=103
|
||||
dport_map_port_16=104
|
||||
dport_map_port_20=105
|
||||
dport_map_port_21=106
|
||||
dport_map_port_22=107
|
||||
dport_map_port_23=108
|
||||
dport_map_port_32=109
|
||||
dport_map_port_33=110
|
||||
dport_map_port_34=111
|
||||
dport_map_port_35=112
|
||||
dport_map_port_124=113
|
||||
dport_map_port_125=114
|
||||
dport_map_port_126=115
|
||||
dport_map_port_127=116
|
||||
dport_map_port_128=117
|
||||
dport_map_port_129=118
|
||||
dport_map_port_130=119
|
||||
dport_map_port_131=120
|
||||
dport_map_port_144=121
|
||||
dport_map_port_145=122
|
||||
dport_map_port_146=123
|
||||
dport_map_port_147=124
|
||||
dport_map_port_148=125
|
||||
dport_map_port_149=126
|
||||
dport_map_port_150=127
|
||||
dport_map_port_151=128
|
||||
|
||||
#firmware load, use fast load
|
||||
load_firmware=0x2
|
||||
|
||||
core_clock_frequency=1325
|
||||
dpr_clock_frequency=1000
|
||||
device_clock_frequency=1325
|
||||
port_flex_enable=1
|
1
device/ragile/x86_64-ragile_ra-b6920-4s-r0/bcm.rc
Normal file
1
device/ragile/x86_64-ragile_ra-b6920-4s-r0/bcm.rc
Normal file
@ -0,0 +1 @@
|
||||
rcload /usr/share/sonic/platform/led_proc_init.soc
|
1
device/ragile/x86_64-ragile_ra-b6920-4s-r0/bcm_pre.rc
Normal file
1
device/ragile/x86_64-ragile_ra-b6920-4s-r0/bcm_pre.rc
Normal file
@ -0,0 +1 @@
|
||||
m0 load 0 0 /usr/share/sonic/platform/linkscan_led.bin
|
BIN
device/ragile/x86_64-ragile_ra-b6920-4s-r0/custom_led.bin
Normal file
BIN
device/ragile/x86_64-ragile_ra-b6920-4s-r0/custom_led.bin
Normal file
Binary file not shown.
1
device/ragile/x86_64-ragile_ra-b6920-4s-r0/default_sku
Normal file
1
device/ragile/x86_64-ragile_ra-b6920-4s-r0/default_sku
Normal file
@ -0,0 +1 @@
|
||||
RA-B6920-4S t1
|
238
device/ragile/x86_64-ragile_ra-b6920-4s-r0/dev.xml
Normal file
238
device/ragile/x86_64-ragile_ra-b6920-4s-r0/dev.xml
Normal file
@ -0,0 +1,238 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!--
|
||||
### type 1 result/1000
|
||||
type 2 result/100
|
||||
type 3 read bit
|
||||
### property need check must add int front
|
||||
-->
|
||||
<catalog>
|
||||
<fans>
|
||||
<fan id="fan1" >
|
||||
<property name="present" location="/sys/bus/i2c/devices/14-000d/fan_present" type="3" bit="0" decode="fanpresent" default="0"/>
|
||||
<property name="status" location="/sys/bus/i2c/devices/14-000d/fan_status1" type="3" bit="0" decode="fanstatus" default="1"/>
|
||||
<property name="fru" e2type="fru" location="/sys/bus/i2c/devices/63-0050/eeprom"/>
|
||||
<!--property name="hw_version" location="/sys/bus/i2c/devices/63-0050/fan_hw_version" type="0" bit="0"/>
|
||||
<property name="fan_type" location="/sys/bus/i2c/devices/63-0050/fan_type"/>
|
||||
<property name="sn" location="/sys/bus/i2c/devices/63-0050/fan_sn"/-->
|
||||
<property name="Speed" location="/sys/bus/i2c/devices/14-000d/hwmon/*/fan1_input"/>
|
||||
</fan>
|
||||
<fan id="fan2" >
|
||||
<property name="present" location="/sys/bus/i2c/devices/13-000d/fan_present" type="3" bit="0" decode="fanpresent" default="0" />
|
||||
<property name="status" location="/sys/bus/i2c/devices/13-000d/fan_status1" type="3" bit="0" decode="fanstatus" default="1"/>
|
||||
<property name="fru" e2type="fru" location="/sys/bus/i2c/devices/55-0050/eeprom"/>
|
||||
<!--property name="hw_version" location="/sys/bus/i2c/devices/55-0050/fan_hw_version" type="0" bit="0"/>
|
||||
<property name="fan_type" location="/sys/bus/i2c/devices/55-0050/fan_type"/>
|
||||
<property name="sn" location="/sys/bus/i2c/devices/55-0050/fan_sn"/-->
|
||||
<property name="Speed" location="/sys/bus/i2c/devices/13-000d/hwmon/*/fan3_input"/>
|
||||
</fan>
|
||||
<fan id="fan3" >
|
||||
<property name="present" location="/sys/bus/i2c/devices/14-000d/fan_present" type="3" bit="1" decode="fanpresent" default="0"/>
|
||||
<property name="status" location="/sys/bus/i2c/devices/14-000d/fan_status1" type="3" bit="1" decode="fanstatus" default="1"/>
|
||||
<property name="fru" e2type="fru" location="/sys/bus/i2c/devices/64-0050/eeprom"/>
|
||||
<!--property name="hw_version" location="/sys/bus/i2c/devices/64-0050/fan_hw_version" type="0" bit="0"/>
|
||||
<property name="fan_type" location="/sys/bus/i2c/devices/64-0050/fan_type"/>
|
||||
<property name="sn" location="/sys/bus/i2c/devices/64-0050/fan_sn"/-->
|
||||
<property name="Speed" location="/sys/bus/i2c/devices/14-000d/hwmon/*/fan5_input"/>
|
||||
</fan>
|
||||
<fan id="fan4" >
|
||||
<property name="present" location="/sys/bus/i2c/devices/13-000d/fan_present" type="3" bit="1" decode="fanpresent" default="0"/>
|
||||
<property name="status" location="/sys/bus/i2c/devices/13-000d/fan_status1" type="3" bit="1" decode="fanstatus" default="1"/>
|
||||
<property name="fru" e2type="fru" location="/sys/bus/i2c/devices/56-0050/eeprom"/>
|
||||
<!--property name="hw_version" location="/sys/bus/i2c/devices/56-0050/fan_hw_version" type="0" bit="0"/>
|
||||
<property name="fan_type" location="/sys/bus/i2c/devices/56-0050/fan_type"/>
|
||||
<property name="sn" location="/sys/bus/i2c/devices/56-0050/fan_sn"/-->
|
||||
<property name="Speed" location="/sys/bus/i2c/devices/13-000d/hwmon/*/fan7_input"/>
|
||||
</fan>
|
||||
<fan id="fan5" >
|
||||
<property name="present" location="/sys/bus/i2c/devices/14-000d/fan_present" type="3" bit="2" decode="fanpresent" default="0"/>
|
||||
<property name="status" location="/sys/bus/i2c/devices/14-000d/fan_status1" type="3" bit="2" decode="fanstatus" default="1"/>
|
||||
<property name="fru" e2type="fru" location="/sys/bus/i2c/devices/65-0050/eeprom"/>
|
||||
<!--property name="hw_version" location="/sys/bus/i2c/devices/65-0050/fan_hw_version" type="0" bit="0"/>
|
||||
<property name="fan_type" location="/sys/bus/i2c/devices/65-0050/fan_type"/>
|
||||
<property name="sn" location="/sys/bus/i2c/devices/65-0050/fan_sn"/-->
|
||||
<property name="Speed" location="/sys/bus/i2c/devices/14-000d/hwmon/*/fan9_input"/>
|
||||
</fan>
|
||||
<fan id="fan6" >
|
||||
<property name="present" location="/sys/bus/i2c/devices/13-000d/fan_present" type="3" bit="2" decode="fanpresent" default="0"/>
|
||||
<property name="status" location="/sys/bus/i2c/devices/13-000d/fan_status1" type="3" bit="2" decode="fanstatus" default="1"/>
|
||||
<property name="fru" e2type="fru" location="/sys/bus/i2c/devices/57-0050/eeprom"/>
|
||||
<!--property name="hw_version" location="/sys/bus/i2c/devices/57-0050/fan_hw_version" type="0" bit="0"/>
|
||||
<property name="fan_type" location="/sys/bus/i2c/devices/57-0050/fan_type"/>
|
||||
<property name="sn" location="/sys/bus/i2c/devices/57-0050/fan_sn"/-->
|
||||
<property name="Speed" location="/sys/bus/i2c/devices/13-000d/hwmon/*/fan11_input"/>
|
||||
</fan>
|
||||
</fans>
|
||||
<temps>
|
||||
<temp id="lm75in" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/29-004f/hwmon/*/temp1_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/29-004f/hwmon/*/temp1_max" type="1" />
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/29-004f/hwmon/*/temp1_crit_hyst" type="1" /-->
|
||||
</temp>
|
||||
<temp id="lm75out" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/28-004b/hwmon/*/temp1_input" type="1" />
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/28-004b/hwmon/*/temp1_max" type="1" />
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/28-004b/hwmon/*/temp1_crit_hyst" type="1" /-->
|
||||
</temp>
|
||||
<temp id="lm75hot" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/28-004c/hwmon/*/temp2_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/28-004c/hwmon/*/temp2_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/28-004c/hwmon/*/temp2_crit_hyst" type="1"/-->
|
||||
</temp>
|
||||
<temp id="slot1lm75a1" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/32-0048/hwmon/*/temp1_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/32-0048/hwmon/*/temp1_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/32-0048/hwmon/*/temp1_crit_hyst" type="1"/-->
|
||||
</temp>
|
||||
<temp id="slot1lm75a2" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/32-0049/hwmon/*/temp1_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/32-0049/hwmon/*/temp1_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/32-0049/hwmon/*/temp1_crit_hyst" type="1"/-->
|
||||
</temp>
|
||||
<temp id="slot1lm75a3" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/32-004d/hwmon/*/temp1_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/32-004d/hwmon/*/temp1_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/32-004d/hwmon/*/temp1_crit_hyst" type="1"/-->
|
||||
</temp>
|
||||
<temp id="slot2lm75a1" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/48-0048/hwmon/*/temp1_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/48-0048/hwmon/*/temp1_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/48-0048/hwmon/*/temp1_crit_hyst" type="1"/-->
|
||||
</temp>
|
||||
<temp id="slot2lm75a2" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/48-0049/hwmon/*/temp1_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/48-0049/hwmon/*/temp1_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/48-0049/hwmon/*/temp1_crit_hyst" type="1"/-->
|
||||
</temp>
|
||||
<temp id="slot2lm75a3" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/48-004d/hwmon/*/temp1_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/48-004d/hwmon/*/temp1_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/48-004d/hwmon/*/temp1_crit_hyst" type="1"/-->
|
||||
</temp>
|
||||
<temp id="slot3lm75a1" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/40-0048/hwmon/*/temp1_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/40-0048/hwmon/*/temp1_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/40-0048/hwmon/*/temp1_crit_hyst" type="1"/-->
|
||||
</temp>
|
||||
<temp id="slot3lm75a2" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/40-0049/hwmon/*/temp1_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/40-0049/hwmon/*/temp1_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/40-0049/hwmon/*/temp1_crit_hyst" type="1"/-->
|
||||
</temp>
|
||||
<temp id="slot3lm75a3" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/40-004d/hwmon/*/temp1_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/40-004d/hwmon/*/temp1_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/40-004d/hwmon/*/temp1_crit_hyst" type="1"/-->
|
||||
</temp>
|
||||
<temp id="slot4lm75a1" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/16-0048/hwmon/*/temp1_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/16-0048/hwmon/*/temp1_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/16-0048/hwmon/*/temp1_crit_hyst" type="1"/-->
|
||||
</temp>
|
||||
<temp id="slot4lm75a2" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/16-0049/hwmon/*/temp1_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/16-0049/hwmon/*/temp1_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/16-0049/hwmon/*/temp1_crit_hyst" type="1"/-->
|
||||
</temp>
|
||||
<temp id="slot4lm75a3" >
|
||||
<property name="temp1_input" location="/sys/bus/i2c/devices/16-004d/hwmon/*/temp1_input" type="1"/>
|
||||
<!--property name="temp1_max" location="/sys/bus/i2c/devices/16-004d/hwmon/*/temp1_max" type="1"/>
|
||||
<property name="temp1_max_hyst" location="/sys/bus/i2c/devices/16-004d/hwmon/*/temp1_crit_hyst" type="1"/-->
|
||||
</temp>
|
||||
</temps>
|
||||
<psus>
|
||||
<psu id="psu1" >
|
||||
<property name="present" location="/sys/devices/pci0000:00/0000:00:1f.0/psu_status_1" type="3" bit="0" decode="psucheck" default="0"/>
|
||||
<property name="status" location="/sys/devices/pci0000:00/0000:00:1f.0/psu_status_1" type="3" bit="1" decode="psustatus" default="1"/>
|
||||
<property name="sn" location="/sys/bus/i2c/devices/23-0050/psu_sn" />
|
||||
<property name="type1" location="/sys/bus/i2c/devices/23-0050/psu_type" decode="psutype"/>
|
||||
<property name="in_current" location="/sys/bus/i2c/devices/23-0058/hwmon/*/curr1_input" type="1" />
|
||||
<property name="in_voltage" location="/sys/bus/i2c/devices/23-0058/hwmon/*/in1_input" type="1"/>
|
||||
<property name="out_voltage" location="/sys/bus/i2c/devices/23-0058/hwmon/*/in2_input" type="1" />
|
||||
<property name="out_current" location="/sys/bus/i2c/devices/23-0058/hwmon/*/curr2_input" type="1" />
|
||||
<property name="temp" location="/sys/bus/i2c/devices/23-0058/hwmon/*/temp1_input" type="1"/>
|
||||
<property name="hw" location="/sys/bus/i2c/devices/23-0050/psu_hw" />
|
||||
</psu>
|
||||
<psu id="psu2" >
|
||||
<property name="present" location="/sys/devices/pci0000:00/0000:00:1f.0/psu_status_2" type="3" bit="0" decode="psucheck" default="0"/>
|
||||
<property name="status" location="/sys/devices/pci0000:00/0000:00:1f.0/psu_status_2" type="3" bit="1" decode="psustatus" default="1"/>
|
||||
<property name="sn" location="/sys/bus/i2c/devices/25-0050/psu_sn" />
|
||||
<property name="type1" location="/sys/bus/i2c/devices/25-0050/psu_type" decode="psutype"/>
|
||||
<property name="in_current" location="/sys/bus/i2c/devices/25-0058/hwmon/*/curr1_input" type="1" />
|
||||
<property name="in_voltage" location="/sys/bus/i2c/devices/25-0058/hwmon/*/in1_input" type="1"/>
|
||||
<property name="out_voltage" location="/sys/bus/i2c/devices/25-0058/hwmon/*/in2_input" type="1" />
|
||||
<property name="out_current" location="/sys/bus/i2c/devices/25-0058/hwmon/*/curr2_input" type="1" />
|
||||
<property name="temp" location="/sys/bus/i2c/devices/25-0058/hwmon/*/temp1_input" type="1"/>
|
||||
<property name="hw" location="/sys/bus/i2c/devices/25-0050/psu_hw" />
|
||||
</psu>
|
||||
<psu id="psu3" >
|
||||
<property name="present" location="/sys/devices/pci0000:00/0000:00:1f.0/psu_status_3" type="3" bit="0" decode="psucheck" default="0"/>
|
||||
<property name="status" location="/sys/devices/pci0000:00/0000:00:1f.0/psu_status_3" type="3" bit="1" decode="psustatus" default="1"/>
|
||||
<property name="sn" location="/sys/bus/i2c/devices/24-0050/psu_sn" />
|
||||
<property name="type1" location="/sys/bus/i2c/devices/24-0050/psu_type" decode="psutype"/>
|
||||
<property name="in_current" location="/sys/bus/i2c/devices/24-0058/hwmon/*/curr1_input" type="1" />
|
||||
<property name="in_voltage" location="/sys/bus/i2c/devices/24-0058/hwmon/*/in1_input" type="1"/>
|
||||
<property name="out_voltage" location="/sys/bus/i2c/devices/24-0058/hwmon/*/in2_input" type="1" />
|
||||
<property name="out_current" location="/sys/bus/i2c/devices/24-0058/hwmon/*/curr2_input" type="1" />
|
||||
<property name="temp" location="/sys/bus/i2c/devices/24-0058/hwmon/*/temp1_input" type="1"/>
|
||||
<property name="hw" location="/sys/bus/i2c/devices/24-0050/psu_hw" />
|
||||
</psu>
|
||||
<psu id="psu4" >
|
||||
<property name="present" location="/sys/devices/pci0000:00/0000:00:1f.0/psu_status_4" type="3" bit="0" decode="psucheck" default="0"/>
|
||||
<property name="status" location="/sys/devices/pci0000:00/0000:00:1f.0/psu_status_4" type="3" bit="1" decode="psustatus" default="1"/>
|
||||
<property name="sn" location="/sys/bus/i2c/devices/26-0050/psu_sn" />
|
||||
<property name="type1" location="/sys/bus/i2c/devices/26-0050/psu_type" decode="psutype"/>
|
||||
<property name="in_current" location="/sys/bus/i2c/devices/26-0058/hwmon/*/curr1_input" type="1" />
|
||||
<property name="in_voltage" location="/sys/bus/i2c/devices/26-0058/hwmon/*/in1_input" type="1"/>
|
||||
<property name="out_voltage" location="/sys/bus/i2c/devices/26-0058/hwmon/*/in2_input" type="1" />
|
||||
<property name="out_current" location="/sys/bus/i2c/devices/26-0058/hwmon/*/curr2_input" type="1" />
|
||||
<property name="temp" location="/sys/bus/i2c/devices/26-0058/hwmon/*/temp1_input" type="1"/>
|
||||
<property name="hw" location="/sys/bus/i2c/devices/26-0050/psu_hw" />
|
||||
</psu>
|
||||
</psus>
|
||||
<slots>
|
||||
<slot id="slot1" >
|
||||
<property name="present" location="/sys/devices/pci0000:00/0000:00:1f.0/slot_present" type="3" bit="4" decode="slotpresent" default="0"/>
|
||||
</slot>
|
||||
<slot id="slot2" >
|
||||
<property name="present" location="/sys/devices/pci0000:00/0000:00:1f.0/slot_present" type="3" bit="5" decode="slotpresent" default="0"/>
|
||||
</slot>
|
||||
<slot id="slot3" >
|
||||
<property name="present" location="/sys/devices/pci0000:00/0000:00:1f.0/slot_present" type="3" bit="6" decode="slotpresent" default="0"/>
|
||||
</slot>
|
||||
<slot id="slot4" >
|
||||
<property name="present" location="/sys/devices/pci0000:00/0000:00:1f.0/slot_present" type="3" bit="7" decode="slotpresent" default="0"/>
|
||||
</slot>
|
||||
</slots>
|
||||
<cpus location="/sys/class/hwmon/hwmon0"/>
|
||||
<decode>
|
||||
<fanpresent>
|
||||
<code key="1" value="ABSENT"/>
|
||||
<code key="0" value="PRESENT"/>
|
||||
</fanpresent>
|
||||
<fanstatus>
|
||||
<code key="1" value="OK"/>
|
||||
<code key="0" value="NOT OK"/>
|
||||
</fanstatus>
|
||||
<psucheck>
|
||||
<code key="1" value="ABSENT"/>
|
||||
<code key="0" value="PRESENT"/>
|
||||
</psucheck>
|
||||
<psustatus>
|
||||
<code key="1" value="OK"/>
|
||||
<code key="0" value="NOT OK"/>
|
||||
</psustatus>
|
||||
|
||||
<psutype>
|
||||
<code key="CSU800AP-3-300" value="RG-PA800I-F"/>
|
||||
<code key="CSU550AP-3-300" value="RG-PA550I-F"/>
|
||||
<code key="FSP1200-20ERM" value="FSP1200-20ERM"/>
|
||||
<code key="DPS-1300AB-6 S" value="DPS-1300AB-6 S"/>
|
||||
|
||||
</psutype>
|
||||
<slotpresent>
|
||||
<code key="1" value="ABSENT"/>
|
||||
<code key="0" value="PRESENT"/>
|
||||
</slotpresent>
|
||||
</decode>
|
||||
</catalog>
|
||||
|
3716
device/ragile/x86_64-ragile_ra-b6920-4s-r0/device_data.json
Normal file
3716
device/ragile/x86_64-ragile_ra-b6920-4s-r0/device_data.json
Normal file
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,2 @@
|
||||
CONSOLE_SPEED=115200
|
||||
ONIE_PLATFORM_EXTRA_CMDLINE_LINUX="intel_pstate=disable intel_idle.max_cstate=0"
|
@ -0,0 +1,7 @@
|
||||
m0 load 0 0x3800 /usr/share/sonic/platform/custom_led.bin
|
||||
|
||||
led auto on
|
||||
|
||||
led start
|
||||
|
||||
linkscan spbm=all force=all interval=250000
|
BIN
device/ragile/x86_64-ragile_ra-b6920-4s-r0/linkscan_led.bin
Normal file
BIN
device/ragile/x86_64-ragile_ra-b6920-4s-r0/linkscan_led.bin
Normal file
Binary file not shown.
63
device/ragile/x86_64-ragile_ra-b6920-4s-r0/minigraph.xml
Normal file
63
device/ragile/x86_64-ragile_ra-b6920-4s-r0/minigraph.xml
Normal file
@ -0,0 +1,63 @@
|
||||
<DeviceMiniGraph xmlns:i="http://www.w3.org/2001/XMLSchema-instance" xmlns="Microsoft.Search.Autopilot.Evolution">
|
||||
<CpgDec>
|
||||
</CpgDec>
|
||||
<DpgDec>
|
||||
<DeviceDataPlaneInfo>
|
||||
<IPSecTunnels/>
|
||||
<LoopbackIPInterfaces/>
|
||||
<ManagementIPInterfaces xmlns:a="http://schemas.datacontract.org/2004/07/Microsoft.Search.Autopilot.Evolution">
|
||||
</ManagementIPInterfaces>
|
||||
<MplsInterfaces/>
|
||||
<MplsTeInterfaces/>
|
||||
<RsvpInterfaces/>
|
||||
<Hostname>switch2</Hostname>
|
||||
<PortChannelInterfaces/>
|
||||
<VlanInterfaces/>
|
||||
<IPInterfaces/>
|
||||
<DataAcls/>
|
||||
<AclInterfaces/>
|
||||
<DownstreamSummaries/>
|
||||
<DownstreamSummarySet xmlns:a="http://schemas.datacontract.org/2004/07/Microsoft.Search.Autopilot.Evolution"/>
|
||||
</DeviceDataPlaneInfo>
|
||||
</DpgDec>
|
||||
<PngDec>
|
||||
<Devices>
|
||||
<Device i:type="LeafRouter">
|
||||
<Hostname>switch2</Hostname>
|
||||
<HwSku>RA-B6920-4S</HwSku>
|
||||
</Device>
|
||||
</Devices>
|
||||
</PngDec>
|
||||
<MetadataDeclaration>
|
||||
<Devices xmlns:a="http://schemas.datacontract.org/2004/07/Microsoft.Search.Autopilot.Evolution">
|
||||
<a:DeviceMetadata>
|
||||
<a:Name>switch2</a:Name>
|
||||
<a:Properties>
|
||||
<a:DeviceProperty>
|
||||
<a:Name>DhcpResources</a:Name>
|
||||
<a:Reference i:nil="true"/>
|
||||
<a:Value></a:Value>
|
||||
</a:DeviceProperty>
|
||||
<a:DeviceProperty>
|
||||
<a:Name>NtpResources</a:Name>
|
||||
<a:Reference i:nil="true"/>
|
||||
<a:Value>0.debian.pool.ntp.org;1.debian.pool.ntp.org;2.debian.pool.ntp.org;3.debian.pool.ntp.org</a:Value>
|
||||
</a:DeviceProperty>
|
||||
<a:DeviceProperty>
|
||||
<a:Name>SyslogResources</a:Name>
|
||||
<a:Reference i:nil="true"/>
|
||||
<a:Value></a:Value>
|
||||
</a:DeviceProperty>
|
||||
<a:DeviceProperty>
|
||||
<a:Name>ErspanDestinationIpv4</a:Name>
|
||||
<a:Reference i:nil="true"/>
|
||||
<a:Value>2.2.2.2</a:Value>
|
||||
</a:DeviceProperty>
|
||||
</a:Properties>
|
||||
</a:DeviceMetadata>
|
||||
</Devices>
|
||||
<Properties xmlns:a="http://schemas.datacontract.org/2004/07/Microsoft.Search.Autopilot.Evolution"/>
|
||||
</MetadataDeclaration>
|
||||
<Hostname>switch2</Hostname>
|
||||
<HwSku>RA-B6920-4S</HwSku>
|
||||
</DeviceMiniGraph>
|
252
device/ragile/x86_64-ragile_ra-b6920-4s-r0/monitor.py
Normal file
252
device/ragile/x86_64-ragile_ra-b6920-4s-r0/monitor.py
Normal file
@ -0,0 +1,252 @@
|
||||
#!/usr/bin/python
|
||||
# -*- coding: UTF-8 -*-
|
||||
# * onboard temperature sensors
|
||||
# * FAN trays
|
||||
# * PSU
|
||||
#
|
||||
import os
|
||||
import xml.etree.ElementTree as ET
|
||||
import glob
|
||||
from eepromutil.fru import *
|
||||
|
||||
MAILBOX_DIR = "/sys/bus/i2c/devices/"
|
||||
CONFIG_NAME = "dev.xml"
|
||||
|
||||
def getPMCreg(location):
|
||||
retval = 'ERR'
|
||||
if (not os.path.isfile(location)):
|
||||
return "%s %s notfound"% (retval , location)
|
||||
try:
|
||||
with open(location, 'r') as fd:
|
||||
retval = fd.read()
|
||||
except Exception as error:
|
||||
pass
|
||||
|
||||
retval = retval.rstrip('\r\n')
|
||||
retval = retval.lstrip(" ")
|
||||
return retval
|
||||
# Get a mailbox register
|
||||
def get_pmc_register(reg_name):
|
||||
retval = 'ERR'
|
||||
mb_reg_file = reg_name
|
||||
filepath = glob.glob(mb_reg_file)
|
||||
if(len(filepath) == 0):
|
||||
return "%s %s notfound"% (retval , mb_reg_file)
|
||||
mb_reg_file = filepath[0]
|
||||
if (not os.path.isfile(mb_reg_file)):
|
||||
#print mb_reg_file, 'not found !'
|
||||
return "%s %s notfound"% (retval , mb_reg_file)
|
||||
try:
|
||||
with open(mb_reg_file, 'r') as fd:
|
||||
retval = fd.read()
|
||||
except Exception as error:
|
||||
pass
|
||||
|
||||
retval = retval.rstrip('\r\n')
|
||||
retval = retval.lstrip(" ")
|
||||
return retval
|
||||
|
||||
class checktype():
|
||||
def __init__(self, test1):
|
||||
self.test1 = test1
|
||||
@staticmethod
|
||||
def check(name,location, bit, value, tips , err1):
|
||||
psu_status = int(get_pmc_register(location),16)
|
||||
val = (psu_status & (1<< bit)) >> bit
|
||||
if (val != value):
|
||||
err1["errmsg"] = tips
|
||||
err1["code"] = -1
|
||||
return -1
|
||||
else:
|
||||
err1["errmsg"] = "none"
|
||||
err1["code"] = 0
|
||||
return 0
|
||||
@staticmethod
|
||||
def getValue(location, bit , type):
|
||||
value_t = get_pmc_register(location)
|
||||
if value_t.startswith("ERR") :
|
||||
return value_t
|
||||
if (type == 1):
|
||||
return float(value_t)/1000
|
||||
elif (type == 2):
|
||||
return float(value_t)/100
|
||||
elif (type == 3):
|
||||
psu_status = int(value_t,16)
|
||||
return (psu_status & (1<< bit)) >> bit
|
||||
elif (type == 4):
|
||||
return int(value_t,10)
|
||||
else:
|
||||
return value_t;
|
||||
#######temp
|
||||
@staticmethod
|
||||
def getTemp(self, name, location , ret_t):
|
||||
ret2 = self.getValue(location + "temp1_input" ," " ,1);
|
||||
ret3 = self.getValue(location + "temp1_max" ," ", 1);
|
||||
ret4 = self.getValue(location + "temp1_max_hyst" ," ", 1);
|
||||
ret_t["temp1_input"] = ret2
|
||||
ret_t["temp1_max"] = ret3
|
||||
ret_t["temp1_max_hyst"] = ret4
|
||||
@staticmethod
|
||||
def getLM75(name, location, result):
|
||||
c1=checktype
|
||||
r1={}
|
||||
c1.getTemp(c1, name, location, r1)
|
||||
result[name] = r1
|
||||
##########fanFRU
|
||||
@staticmethod
|
||||
def decodeBinByValue(retval):
|
||||
fru = ipmifru()
|
||||
fru.decodeBin(retval)
|
||||
return fru
|
||||
|
||||
@staticmethod
|
||||
def printbinvalue(b):
|
||||
index = 0
|
||||
print " ",
|
||||
for width in range(16):
|
||||
print "%02x " % width,
|
||||
print ""
|
||||
for i in range(0, len(b)):
|
||||
if index % 16 == 0:
|
||||
print " "
|
||||
print " %02x " % i,
|
||||
print "%02x " % ord(b[i]),
|
||||
index += 1
|
||||
print ""
|
||||
|
||||
@staticmethod
|
||||
def getfruValue(val):
|
||||
binval = checktype.getValue(val, 0 , 0)
|
||||
fanpro = {}
|
||||
ret = checktype.decodeBinByValue(binval)
|
||||
fanpro['fan_type'] = ret.productInfoArea.productName
|
||||
fanpro['hw_version'] = int(ret.productInfoArea.productVersion, 16)
|
||||
fanpro['sn'] = ret.productInfoArea.productSerialNumber
|
||||
fanpro['fanid'] = ret.productInfoArea.productextra2
|
||||
return fanpro
|
||||
|
||||
|
||||
class status():
|
||||
def __init__(self, productname):
|
||||
self.productname = productname
|
||||
|
||||
@staticmethod
|
||||
def getETroot(filename):
|
||||
tree = ET.parse(filename)
|
||||
root = tree.getroot()
|
||||
return root;
|
||||
|
||||
@staticmethod
|
||||
def getDecodValue(collection, decode):
|
||||
decodes = collection.find('decode')
|
||||
testdecode = decodes.find(decode)
|
||||
test={}
|
||||
for neighbor in testdecode.iter('code'):
|
||||
test[neighbor.attrib["key"]]=neighbor.attrib["value"]
|
||||
return test
|
||||
@staticmethod
|
||||
def getfileValue(location):
|
||||
return checktype.getValue(location," "," ")
|
||||
@staticmethod
|
||||
def getETValue(a, filename, tagname):
|
||||
root = status.getETroot(filename)
|
||||
for neighbor in root.iter(tagname):
|
||||
prob_t = {}
|
||||
prob_t = neighbor.attrib
|
||||
prob_t['errcode']= 0
|
||||
prob_t['errmsg'] = ''
|
||||
for pros in neighbor.iter("property"):
|
||||
ret = dict(neighbor.attrib.items() + pros.attrib.items())
|
||||
if ret.get('e2type') == 'fru' and ret.get("name") == "fru":
|
||||
fruval = checktype.getfruValue(ret["location"])
|
||||
prob_t.update(fruval)
|
||||
if ('type' not in ret.keys()):
|
||||
val = "0";
|
||||
else:
|
||||
val = ret["type"]
|
||||
if ('bit' not in ret.keys()):
|
||||
bit = "0";
|
||||
else:
|
||||
bit = ret["bit"]
|
||||
s = checktype.getValue(ret["location"], int(bit),int(val))
|
||||
if isinstance(s, str) and s.startswith("ERR"):
|
||||
prob_t['errcode']= -1
|
||||
prob_t['errmsg']= s
|
||||
if ('default' in ret.keys()):
|
||||
rt = status.getDecodValue(root,ret['decode'])
|
||||
prob_t['errmsg']= rt[str(s)]
|
||||
if str(s) != ret["default"]:
|
||||
prob_t['errcode']= -1
|
||||
break;
|
||||
else:
|
||||
if ('decode' in ret.keys()):
|
||||
rt = status.getDecodValue(root,ret['decode'])
|
||||
if(ret['decode'] == "psutype" and s.replace("\x00","").rstrip() not in rt.keys()):
|
||||
prob_t['errcode']= -1
|
||||
prob_t['errmsg'] = '%s'% ("Not supported PSU")
|
||||
else:
|
||||
s = rt[str(s).replace("\x00","").rstrip()]
|
||||
name = ret["name"]
|
||||
prob_t[name]=str(s)
|
||||
a.append(prob_t)
|
||||
@staticmethod
|
||||
def getCPUValue(a, filename, tagname):
|
||||
root = status.getETroot(filename)
|
||||
for neighbor in root.iter(tagname):
|
||||
location = neighbor.attrib["location"]
|
||||
L=[]
|
||||
for dirpath, dirnames, filenames in os.walk(location):
|
||||
for file in filenames :
|
||||
if file.endswith("input"):
|
||||
L.append(os.path.join(dirpath, file))
|
||||
L =sorted(L,reverse=False)
|
||||
for i in range(len(L)):
|
||||
prob_t = {}
|
||||
prob_t["name"] = getPMCreg("%s/temp%d_label"%(location,i+1))
|
||||
prob_t["temp"] = float(getPMCreg("%s/temp%d_input"%(location,i+1)))/1000
|
||||
prob_t["alarm"] = float(getPMCreg("%s/temp%d_crit_alarm"%(location,i+1)))/1000
|
||||
prob_t["crit"] = float(getPMCreg("%s/temp%d_crit"%(location,i+1)))/1000
|
||||
prob_t["max"] = float(getPMCreg("%s/temp%d_max"%(location,i+1)))/1000
|
||||
a.append(prob_t)
|
||||
|
||||
@staticmethod
|
||||
def getFileName():
|
||||
return os.path.dirname(os.path.realpath(__file__)) + "/"+ CONFIG_NAME
|
||||
@staticmethod
|
||||
def getFan(ret):
|
||||
_filename = status.getFileName()
|
||||
_tagname = "fan"
|
||||
status.getvalue(ret, _filename, _tagname)
|
||||
@staticmethod
|
||||
def checkFan(ret):
|
||||
_filename = status.getFileName()
|
||||
# _filename = "/usr/local/bin/" + status.getFileName()
|
||||
_tagname = "fan"
|
||||
status.getETValue(ret, _filename, _tagname)
|
||||
@staticmethod
|
||||
def getTemp(ret):
|
||||
_filename = status.getFileName()
|
||||
#_filename = "/usr/local/bin/" + status.getFileName()
|
||||
_tagname = "temp"
|
||||
status.getETValue(ret, _filename, _tagname)
|
||||
@staticmethod
|
||||
def getPsu(ret):
|
||||
_filename = status.getFileName()
|
||||
# _filename = "/usr/local/bin/" + status.getFileName()
|
||||
_tagname = "psu"
|
||||
status.getETValue(ret, _filename, _tagname)
|
||||
|
||||
@staticmethod
|
||||
def getcputemp(ret):
|
||||
_filename = status.getFileName()
|
||||
_tagname = "cpus"
|
||||
status.getCPUValue(ret, _filename, _tagname)
|
||||
|
||||
@staticmethod
|
||||
def checkSlot(ret):
|
||||
_filename = status.getFileName()
|
||||
# _filename = "/usr/local/bin/" + status.getFileName()
|
||||
_tagname = "slot"
|
||||
status.getETValue(ret, _filename, _tagname)
|
||||
|
||||
|
@ -0,0 +1,67 @@
|
||||
{
|
||||
"XCVR": {
|
||||
"xcvr_present": {
|
||||
"i2c": {
|
||||
"valmap-SFP28": {
|
||||
"1": true,
|
||||
"0": false
|
||||
},
|
||||
"valmap-QSFP28": {
|
||||
"1": true,
|
||||
"0": false
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
"PSU": {
|
||||
"psu_present": {
|
||||
"i2c": {
|
||||
"valmap": {
|
||||
"1": true,
|
||||
"0": false
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
"psu_power_good": {
|
||||
"i2c": {
|
||||
"valmap": {
|
||||
"1": true,
|
||||
"0": false
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
"psu_fan_dir": {
|
||||
"i2c": {
|
||||
"valmap": {
|
||||
"F2B": "EXHAUST",
|
||||
"B2F": "INTAKE"
|
||||
}
|
||||
}
|
||||
},
|
||||
"PSU_FAN_MAX_SPEED": "18000"
|
||||
},
|
||||
|
||||
"FAN": {
|
||||
"direction": {
|
||||
"i2c": {
|
||||
"valmap": {
|
||||
"1": "INTAKE",
|
||||
"0": "EXHAUST"
|
||||
}
|
||||
}
|
||||
},
|
||||
"present": {
|
||||
"i2c": {
|
||||
"valmap": {
|
||||
"1": true,
|
||||
"0": false
|
||||
}
|
||||
}
|
||||
},
|
||||
"duty_cycle_to_pwm": "lambda dc: dc*255/100",
|
||||
"pwm_to_duty_cycle": "lambda pwm: pwm*100/255"
|
||||
}
|
||||
}
|
13877
device/ragile/x86_64-ragile_ra-b6920-4s-r0/pddf/pddf-device.json
Executable file
13877
device/ragile/x86_64-ragile_ra-b6920-4s-r0/pddf/pddf-device.json
Executable file
File diff suppressed because it is too large
Load Diff
1
device/ragile/x86_64-ragile_ra-b6920-4s-r0/platform_asic
Normal file
1
device/ragile/x86_64-ragile_ra-b6920-4s-r0/platform_asic
Normal file
@ -0,0 +1 @@
|
||||
broadcom
|
@ -0,0 +1,21 @@
|
||||
{
|
||||
"chassis": {
|
||||
"RA-B6510-32C": {
|
||||
"component": {
|
||||
"COMPONENT-1": {},
|
||||
"COMPONENT-2": {},
|
||||
"COMPONENT-3": {},
|
||||
"COMPONENT-4": {},
|
||||
"COMPONENT-5": {},
|
||||
"COMPONENT-6": {},
|
||||
"COMPONENT-7": {},
|
||||
"COMPONENT-8": {},
|
||||
"COMPONENT-9": {},
|
||||
"COMPONENT-10": {},
|
||||
"COMPONENT-11": {},
|
||||
"COMPONENT-12": {},
|
||||
"COMPONENT-13": {}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
13
device/ragile/x86_64-ragile_ra-b6920-4s-r0/plugins/eeprom.py
Normal file
13
device/ragile/x86_64-ragile_ra-b6920-4s-r0/plugins/eeprom.py
Normal file
@ -0,0 +1,13 @@
|
||||
#!/usr/bin/env python
|
||||
|
||||
try:
|
||||
from sonic_eeprom import eeprom_tlvinfo
|
||||
except ImportError as e:
|
||||
raise ImportError (str(e) + "- required module not found")
|
||||
|
||||
|
||||
class board(eeprom_tlvinfo.TlvInfoDecoder):
|
||||
|
||||
def __init__(self, name, path, cpld_root, ro):
|
||||
self.eeprom_path = "/sys/bus/i2c/devices/1-0056/eeprom"
|
||||
super(board, self).__init__(self.eeprom_path, 0, '', True)
|
@ -0,0 +1,59 @@
|
||||
#
|
||||
# psuutil.py
|
||||
# Platform-specific PSU status interface for SONiC
|
||||
#
|
||||
|
||||
try:
|
||||
from sonic_psu.psu_base import PsuBase
|
||||
except ImportError as e:
|
||||
raise ImportError(str(e) + "- required module not found")
|
||||
|
||||
|
||||
class PsuUtil(PsuBase):
|
||||
"""Platform-specific PSUutil class"""
|
||||
|
||||
def __init__(self):
|
||||
PsuBase.__init__(self)
|
||||
|
||||
def get_num_psus(self):
|
||||
return 4
|
||||
|
||||
def get_psu_status(self, index):
|
||||
if index < 1 or index > 4:
|
||||
return False
|
||||
|
||||
path_tmp = "/sys/devices/pci0000:00/0000:00:1f.0/psu_status_"
|
||||
psu_path = "%s%d"%(path_tmp, index)
|
||||
|
||||
try:
|
||||
data = open(psu_path, "rb")
|
||||
except IOError:
|
||||
return False
|
||||
|
||||
result = int(data.read(2), 16)
|
||||
data.close()
|
||||
|
||||
if (result & 0x2):
|
||||
return True
|
||||
|
||||
return False
|
||||
|
||||
def get_psu_presence(self, index):
|
||||
if index < 1 or index > 4:
|
||||
return False
|
||||
|
||||
path_tmp = "/sys/devices/pci0000:00/0000:00:1f.0/psu_status_"
|
||||
psu_path = "%s%d"%(path_tmp, index)
|
||||
|
||||
try:
|
||||
data = open(psu_path, "rb")
|
||||
except IOError:
|
||||
return False
|
||||
|
||||
result = int(data.read(2), 16)
|
||||
data.close()
|
||||
|
||||
if (result & 0x1) == 0:
|
||||
return True
|
||||
|
||||
return False
|
255
device/ragile/x86_64-ragile_ra-b6920-4s-r0/plugins/sfputil.py
Normal file
255
device/ragile/x86_64-ragile_ra-b6920-4s-r0/plugins/sfputil.py
Normal file
@ -0,0 +1,255 @@
|
||||
# sfputil.py
|
||||
#
|
||||
# Platform-specific SFP transceiver interface for SONiC
|
||||
#
|
||||
|
||||
try:
|
||||
import time
|
||||
import os
|
||||
from sonic_sfp.sfputilbase import SfpUtilBase
|
||||
except ImportError as e:
|
||||
raise ImportError("%s - required module not found" % str(e))
|
||||
|
||||
|
||||
class SfpUtil(SfpUtilBase):
|
||||
"""Platform-specific SfpUtil class"""
|
||||
|
||||
PORT_START = 0
|
||||
PORT_END = 127
|
||||
PORT_QSFP_START = 0
|
||||
PORTS_IN_BLOCK = 128
|
||||
|
||||
EEPROM_OFFSET = 71
|
||||
SFP_DEVICE_TYPE = "optoe2"
|
||||
QSFP_DEVICE_TYPE = "optoe1"
|
||||
I2C_MAX_ATTEMPT = 3
|
||||
|
||||
SFP_STATUS_INSERTED = '1'
|
||||
SFP_STATUS_REMOVED = '0'
|
||||
|
||||
_port_to_eeprom_mapping = {}
|
||||
port_to_i2cbus_mapping ={}
|
||||
port_dict = {}
|
||||
|
||||
@property
|
||||
def port_start(self):
|
||||
return self.PORT_START
|
||||
|
||||
@property
|
||||
def port_end(self):
|
||||
return self.PORT_END
|
||||
|
||||
@property
|
||||
def qsfp_ports(self):
|
||||
return range(self.PORT_QSFP_START, self.PORTS_IN_BLOCK)
|
||||
|
||||
@property
|
||||
def port_to_eeprom_mapping(self):
|
||||
return self._port_to_eeprom_mapping
|
||||
|
||||
def __init__(self):
|
||||
for x in range(self.PORT_START, self.PORTS_IN_BLOCK):
|
||||
self.port_to_i2cbus_mapping[x] = (x + self.EEPROM_OFFSET)
|
||||
if self.get_presence(x):
|
||||
self.port_dict[x] = self.SFP_STATUS_INSERTED
|
||||
else:
|
||||
self.port_dict[x] = self.SFP_STATUS_REMOVED
|
||||
SfpUtilBase.__init__(self)
|
||||
|
||||
def _sfp_read_file_path(self, file_path, offset, num_bytes):
|
||||
attempts = 0
|
||||
while attempts < self.I2C_MAX_ATTEMPT:
|
||||
try:
|
||||
file_path.seek(offset)
|
||||
read_buf = file_path.read(num_bytes)
|
||||
except Exception:
|
||||
attempts += 1
|
||||
time.sleep(0.05)
|
||||
else:
|
||||
return True, read_buf
|
||||
return False, None
|
||||
|
||||
def _sfp_eeprom_present(self, sysfs_sfp_i2c_client_eeprompath, offset):
|
||||
"""Tries to read the eeprom file to determine if the
|
||||
device/sfp is present or not. If sfp present, the read returns
|
||||
valid bytes. If not, read returns error 'Connection timed out"""
|
||||
|
||||
if not os.path.exists(sysfs_sfp_i2c_client_eeprompath):
|
||||
return False
|
||||
else:
|
||||
with open(sysfs_sfp_i2c_client_eeprompath, "rb", buffering=0) as sysfsfile:
|
||||
rv, buf = self._sfp_read_file_path(sysfsfile, offset, 1)
|
||||
return rv
|
||||
|
||||
def _add_new_sfp_device(self, sysfs_sfp_i2c_adapter_path, devaddr, devtype):
|
||||
try:
|
||||
sysfs_nd_path = "%s/new_device" % sysfs_sfp_i2c_adapter_path
|
||||
|
||||
# Write device address to new_device file
|
||||
nd_file = open(sysfs_nd_path, "w")
|
||||
nd_str = "%s %s" % (devtype, hex(devaddr))
|
||||
nd_file.write(nd_str)
|
||||
nd_file.close()
|
||||
|
||||
except Exception as err:
|
||||
print("Error writing to new device file: %s" % str(err))
|
||||
return 1
|
||||
else:
|
||||
return 0
|
||||
|
||||
def _get_port_eeprom_path(self, port_num, devid):
|
||||
sysfs_i2c_adapter_base_path = ""
|
||||
|
||||
if port_num in self.port_to_eeprom_mapping.keys():
|
||||
sysfs_sfp_i2c_client_eeprom_path = self.port_to_eeprom_mapping[port_num]
|
||||
else:
|
||||
sysfs_i2c_adapter_base_path = "/sys/class/i2c-adapter"
|
||||
|
||||
i2c_adapter_id = self._get_port_i2c_adapter_id(port_num)
|
||||
if i2c_adapter_id is None:
|
||||
print("Error getting i2c bus num")
|
||||
return None
|
||||
|
||||
# Get i2c virtual bus path for the sfp
|
||||
sysfs_sfp_i2c_adapter_path = "%s/i2c-%s" % (sysfs_i2c_adapter_base_path,
|
||||
str(i2c_adapter_id))
|
||||
|
||||
# If i2c bus for port does not exist
|
||||
if not os.path.exists(sysfs_sfp_i2c_adapter_path):
|
||||
print("Could not find i2c bus %s. Driver not loaded?" % sysfs_sfp_i2c_adapter_path)
|
||||
return None
|
||||
|
||||
sysfs_sfp_i2c_client_path = "%s/%s-00%s" % (sysfs_sfp_i2c_adapter_path,
|
||||
str(i2c_adapter_id),
|
||||
hex(devid)[-2:])
|
||||
|
||||
# If sfp device is not present on bus, Add it
|
||||
if not os.path.exists(sysfs_sfp_i2c_client_path):
|
||||
if port_num in self.qsfp_ports:
|
||||
ret = self._add_new_sfp_device(
|
||||
sysfs_sfp_i2c_adapter_path, devid, self.QSFP_DEVICE_TYPE)
|
||||
else:
|
||||
ret = self._add_new_sfp_device(
|
||||
sysfs_sfp_i2c_adapter_path, devid, self.SFP_DEVICE_TYPE)
|
||||
if ret != 0:
|
||||
print("Error adding sfp device")
|
||||
return None
|
||||
|
||||
sysfs_sfp_i2c_client_eeprom_path = "%s/eeprom" % sysfs_sfp_i2c_client_path
|
||||
|
||||
return sysfs_sfp_i2c_client_eeprom_path
|
||||
|
||||
def _read_eeprom_specific_bytes(self, sysfsfile_eeprom, offset, num_bytes):
|
||||
eeprom_raw = []
|
||||
for i in range(0, num_bytes):
|
||||
eeprom_raw.append("0x00")
|
||||
|
||||
rv, raw = self._sfp_read_file_path(sysfsfile_eeprom, offset, num_bytes)
|
||||
if rv == False:
|
||||
return None
|
||||
|
||||
try:
|
||||
for n in range(0, num_bytes):
|
||||
eeprom_raw[n] = hex(ord(raw[n]))[2:].zfill(2)
|
||||
except Exception:
|
||||
return None
|
||||
|
||||
return eeprom_raw
|
||||
|
||||
def get_eeprom_dom_raw(self, port_num):
|
||||
if port_num in self.qsfp_ports:
|
||||
# QSFP DOM EEPROM is also at addr 0x50 and thus also stored in eeprom_ifraw
|
||||
return None
|
||||
else:
|
||||
# Read dom eeprom at addr 0x51
|
||||
return self._read_eeprom_devid(port_num, self.IDENTITY_EEPROM_ADDR, 256)
|
||||
|
||||
def get_presence(self, port_num):
|
||||
# Check for invalid port_num
|
||||
#return True
|
||||
if port_num < self.port_start or port_num > self.port_end:
|
||||
return False
|
||||
|
||||
PRESENCE_OFFSET = 3
|
||||
presence_path = "/sys/bus/i2c/devices/%d-003%d/sfp_presence%d" % ((PRESENCE_OFFSET + (port_num // 32)),
|
||||
((port_num % 32) // 16), (((port_num % 32) // 8) + 1))
|
||||
try:
|
||||
data = open(presence_path, "rb")
|
||||
except IOError:
|
||||
return False
|
||||
|
||||
presence_data = data.read(2)
|
||||
if presence_data != "":
|
||||
result = int(presence_data, 16)
|
||||
else :
|
||||
return False
|
||||
data.close()
|
||||
|
||||
# ModPrsL is active low
|
||||
if result & (1 << (port_num % 8)) == 0:
|
||||
return True
|
||||
|
||||
return False
|
||||
|
||||
def get_low_power_mode(self, port_num):
|
||||
# Check for invalid port_num
|
||||
|
||||
return True
|
||||
|
||||
def set_low_power_mode(self, port_num, lpmode):
|
||||
# Check for invalid port_num
|
||||
|
||||
return True
|
||||
|
||||
def reset(self, port_num):
|
||||
# Check for invalid port_num
|
||||
if port_num < self.port_start or port_num > self.port_end:
|
||||
return False
|
||||
|
||||
return True
|
||||
|
||||
def get_transceiver_change_event(self, timeout=0):
|
||||
|
||||
start_time = time.time()
|
||||
currernt_port_dict = {}
|
||||
forever = False
|
||||
|
||||
if timeout == 0:
|
||||
forever = True
|
||||
elif timeout > 0:
|
||||
timeout = timeout / float(1000) # Convert to secs
|
||||
else:
|
||||
print ("get_transceiver_change_event:Invalid timeout value", timeout)
|
||||
return False, {}
|
||||
|
||||
end_time = start_time + timeout
|
||||
if start_time > end_time:
|
||||
print ('get_transceiver_change_event:' \
|
||||
'time wrap / invalid timeout value', timeout)
|
||||
|
||||
return False, {} # Time wrap or possibly incorrect timeout
|
||||
|
||||
while timeout >= 0:
|
||||
# Check for OIR events and return updated port_dict
|
||||
for x in range(self.PORT_START, self.PORTS_IN_BLOCK):
|
||||
if self.get_presence(x):
|
||||
currernt_port_dict[x] = self.SFP_STATUS_INSERTED
|
||||
else:
|
||||
currernt_port_dict[x] = self.SFP_STATUS_REMOVED
|
||||
if (currernt_port_dict == self.port_dict):
|
||||
if forever:
|
||||
time.sleep(1)
|
||||
else:
|
||||
timeout = end_time - time.time()
|
||||
if timeout >= 1:
|
||||
time.sleep(1) # We poll at 1 second granularity
|
||||
else:
|
||||
if timeout > 0:
|
||||
time.sleep(timeout)
|
||||
return True, {}
|
||||
else:
|
||||
# Update reg value
|
||||
self.port_dict = currernt_port_dict
|
||||
return True, self.port_dict
|
||||
print ("get_transceiver_change_event: Should not reach here.")
|
||||
return False, {}
|
@ -0,0 +1,98 @@
|
||||
#
|
||||
# ssd_health
|
||||
#
|
||||
|
||||
from sonic_platform_base.sonic_ssd.ssd_base import SsdBase
|
||||
from subprocess import Popen, PIPE
|
||||
from re import findall
|
||||
from os.path import exists
|
||||
|
||||
INNODISK = "iSmart -d {}"
|
||||
NOT_AVAILABLE = "N/A"
|
||||
|
||||
class SsdUtil(SsdBase):
|
||||
|
||||
def __init__(self, diskdev):
|
||||
"""
|
||||
Constructor
|
||||
Args:
|
||||
diskdev: Linux device name to get parameters for
|
||||
"""
|
||||
if not isinstance(diskdev, str):
|
||||
raise TypeError("disk dev type wrong {}".format(type(diskdev)))
|
||||
|
||||
if not exists(diskdev):
|
||||
raise RuntimeError("disk dev {} not found".format(diskdev))
|
||||
|
||||
self.model = NOT_AVAILABLE
|
||||
self.serial = NOT_AVAILABLE
|
||||
self.firmware = NOT_AVAILABLE
|
||||
self.temperature = NOT_AVAILABLE
|
||||
self.health = NOT_AVAILABLE
|
||||
|
||||
self.ssd_info = self._execute_shell(INNODISK.format(diskdev))
|
||||
|
||||
self.model = self._parse_re(r'Model Name:\s*(.+?)\n', self.ssd_info)
|
||||
self.serial = self._parse_re(r'Serial Number:\s*(.+?)\n', self.ssd_info)
|
||||
self.firmware = self._parse_re(r'FW Version:\s*(.+?)\n', self.ssd_info)
|
||||
self.temperature = self._parse_re(r'Temperature\s*\[\s*(.+?)\]', self.ssd_info)
|
||||
self.health = self._parse_re(r'Health:\s*(.+?)', self.ssd_info)
|
||||
|
||||
def _execute_shell(self, cmd):
|
||||
process = Popen(cmd.split(), universal_newlines=True, stdout=PIPE)
|
||||
output, _ = process.communicate()
|
||||
return output
|
||||
|
||||
def _parse_re(self, pattern, buffer):
|
||||
res_list = findall(pattern, buffer)
|
||||
return res_list[0] if res_list else NOT_AVAILABLE
|
||||
|
||||
def get_health(self):
|
||||
"""
|
||||
Retrieves current disk health in percentages
|
||||
Returns:
|
||||
A float number of current ssd health
|
||||
e.g. 83.5
|
||||
"""
|
||||
return self.health
|
||||
|
||||
def get_temperature(self):
|
||||
"""
|
||||
Retrieves current disk temperature in Celsius
|
||||
Returns:
|
||||
A float number of current temperature in Celsius
|
||||
e.g. 40.1
|
||||
"""
|
||||
return self.temperature
|
||||
|
||||
def get_model(self):
|
||||
"""
|
||||
Retrieves model for the given disk device
|
||||
Returns:
|
||||
A string holding disk model as provided by the manufacturer
|
||||
"""
|
||||
return self.model
|
||||
|
||||
def get_firmware(self):
|
||||
"""
|
||||
Retrieves firmware version for the given disk device
|
||||
Returns:
|
||||
A string holding disk firmware version as provided by the manufacturer
|
||||
"""
|
||||
return self.firmware
|
||||
|
||||
def get_serial(self):
|
||||
"""
|
||||
Retrieves serial number for the given disk device
|
||||
Returns:
|
||||
A string holding disk serial number as provided by the manufacturer
|
||||
"""
|
||||
return self.serial
|
||||
|
||||
def get_vendor_output(self):
|
||||
"""
|
||||
Retrieves vendor specific data for the given disk device
|
||||
Returns:
|
||||
A string holding some vendor specific disk information
|
||||
"""
|
||||
return self.ssd_info
|
@ -0,0 +1,3 @@
|
||||
{
|
||||
"skip_ledd": true
|
||||
}
|
14
device/ragile/x86_64-ragile_ra-b6920-4s-r0/sensors.conf
Normal file
14
device/ragile/x86_64-ragile_ra-b6920-4s-r0/sensors.conf
Normal file
@ -0,0 +1,14 @@
|
||||
chip "rg_cpld-*"
|
||||
label fan1 "fan1_inlet"
|
||||
label fan2 "fan1_outlet"
|
||||
label fan3 "fan2_inlet"
|
||||
label fan4 "fan2_outlet"
|
||||
label fan5 "fan3_inlet"
|
||||
label fan6 "fan3_outlet"
|
||||
label fan7 "fan4_inlet"
|
||||
label fan8 "fan4_outlet"
|
||||
label fan9 "fan5_inlet"
|
||||
label fan10 "fan5_outlet"
|
||||
label fan11 "fan6_inlet"
|
||||
label fan12 "fan6_outlet"
|
||||
|
43
device/ragile/x86_64-ragile_ra-b6920-4s-r0/systest.py
Normal file
43
device/ragile/x86_64-ragile_ra-b6920-4s-r0/systest.py
Normal file
@ -0,0 +1,43 @@
|
||||
#!/usr/bin/python
|
||||
# -*- coding: UTF-8 -*-
|
||||
|
||||
# * onboard interval check
|
||||
# * FAN trays
|
||||
# * PSU
|
||||
# * temp
|
||||
import time
|
||||
import datetime
|
||||
from monitor import status
|
||||
|
||||
def doWork():
|
||||
a=[];
|
||||
'''
|
||||
return: [{'status': '1', 'hw_version': '1.00', 'errcode': 0, 'fan_type': 'M6510-FAN-F', 'errmsg': 'OK', 'Speed': '9778', 'id': 'fan1', 'present': '0', 'sn': '1000000000014'},
|
||||
{'id': 'fan2', 'errmsg': 'not present', 'errcode': -1},
|
||||
{'id': 'fan3', 'errmsg': 'not present', 'errcode': -1},
|
||||
{'id': 'fan4', 'errmsg': 'not present', 'errcode': -1}
|
||||
]
|
||||
description: 1.get id
|
||||
2.errcode equal 0 : dev normal
|
||||
not equal 0 : get errmsg
|
||||
3.other message add when all check success
|
||||
'''
|
||||
status.checkFan(a)
|
||||
#status.getTemp(a)
|
||||
#status.getPsu(a)
|
||||
|
||||
nowTime=datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
|
||||
print nowTime
|
||||
print a
|
||||
def run(interval):
|
||||
while True:
|
||||
try:
|
||||
time_remaining = interval - time.time()%interval
|
||||
time.sleep(time_remaining)
|
||||
doWork()
|
||||
except Exception as e:
|
||||
print(e)
|
||||
|
||||
if __name__ == '__main__':
|
||||
interval = 1
|
||||
run(interval)
|
@ -76,6 +76,8 @@ $(SONIC_ONE_IMAGE)_LAZY_INSTALLS += $(DELL_S6000_PLATFORM_MODULE) \
|
||||
$(RUIJIE_B6510_48VS8CQ_PLATFORM_MODULE) \
|
||||
$(RAGILE_RA_B6510_48V8C_PLATFORM_MODULE) \
|
||||
$(RAGILE_RA_B6910_64C_PLATFORM_MODULE) \
|
||||
$(RAGILE_RA_B6510_32C_PLATFORM_MODULE) \
|
||||
$(RAGILE_RA_B6920_4S_PLATFORM_MODULE) \
|
||||
$(NOKIA_IXR7250_PLATFORM_MODULE)
|
||||
$(SONIC_ONE_IMAGE)_LAZY_BUILD_INSTALLS = $(BRCM_OPENNSL_KERNEL) $(BRCM_DNX_OPENNSL_KERNEL)
|
||||
ifeq ($(INSTALL_DEBUG_TOOLS),y)
|
||||
|
@ -17,3 +17,18 @@ RAGILE_RA_B6910_64C_PLATFORM_MODULE = platform-modules-ragile-ra-b6910-64c_$(RAG
|
||||
$(RAGILE_RA_B6910_64C_PLATFORM_MODULE)_PLATFORM = x86_64-ragile_ra-b6910-64c-r0
|
||||
$(eval $(call add_extra_package,$(RAGILE_RA_B6510_48V8C_PLATFORM_MODULE),$(RAGILE_RA_B6910_64C_PLATFORM_MODULE)))
|
||||
|
||||
## RA-B6510-32C
|
||||
RAGILE_RA_B6510_32C_PLATFORM_MODULE_VERSION = 1.0
|
||||
export RAGILE_RA_B6510_32C_PLATFORM_MODULE_VERSION
|
||||
|
||||
RAGILE_RA_B6510_32C_PLATFORM_MODULE = platform-modules-ragile-ra-b6510-32c_$(RAGILE_RA_B6510_32C_PLATFORM_MODULE_VERSION)_amd64.deb
|
||||
$(RAGILE_RA_B6510_32C_PLATFORM_MODULE)_PLATFORM = x86_64-ragile_ra-b6510-32c-r0
|
||||
$(eval $(call add_extra_package,$(RAGILE_RA_B6510_48V8C_PLATFORM_MODULE),$(RAGILE_RA_B6510_32C_PLATFORM_MODULE)))
|
||||
|
||||
## RA-B6920-4s
|
||||
RAGILE_RA_B6920_4S_PLATFORM_MODULE_VERSION = 1.0
|
||||
export RAGILE_RA_B6920_4S_PLATFORM_MODULE_VERSION
|
||||
|
||||
RAGILE_RA_B6920_4S_PLATFORM_MODULE = platform-modules-ragile-ra-b6920-4s_$(RAGILE_RA_B6920_4S_PLATFORM_MODULE_VERSION)_amd64.deb
|
||||
$(RAGILE_RA_B6920_4S_PLATFORM_MODULE)_PLATFORM = x86_64-ragile_ra-b6920-4s-r0
|
||||
$(eval $(call add_extra_package,$(RAGILE_RA_B6510_48V8C_PLATFORM_MODULE),$(RAGILE_RA_B6920_4S_PLATFORM_MODULE)))
|
||||
|
@ -5,3 +5,11 @@ obj-m += ragile_platform.o
|
||||
obj-m += i2c-mux-pca9641.o
|
||||
obj-m += i2c-mux-pca954x.o
|
||||
obj-m += csu550.o
|
||||
ragile_common-objs := ragile_common_module.o
|
||||
obj-m += ragile_common.o
|
||||
obj-m += fpga_pcie_i2c.o
|
||||
obj-m += fpga_i2c_ocores.o
|
||||
obj-m += lpc_dbg.o
|
||||
obj-m += lpc_cpld_i2c_ocores.o
|
||||
obj-m += rg-i2c-algo-bit.o
|
||||
obj-m += rg-i2c-gpio.o
|
||||
|
906
platform/broadcom/sonic-platform-modules-ragile/common/modules/fpga_i2c_ocores.c
Executable file
906
platform/broadcom/sonic-platform-modules-ragile/common/modules/fpga_i2c_ocores.c
Executable file
@ -0,0 +1,906 @@
|
||||
/*
|
||||
* i2c-ocores.c: I2C bus driver for OpenCores I2C controller
|
||||
* (http://www.opencores.org/projects.cgi/web/i2c/overview).
|
||||
*
|
||||
* Peter Korsgaard <jacmet@sunsite.dk>
|
||||
*
|
||||
* Support for the GRLIB port of the controller by
|
||||
* Andreas Larsson <andreas@gaisler.com>
|
||||
*
|
||||
* This file is licensed under the terms of the GNU General Public License
|
||||
* version 2. This program is licensed "as is" without any warranty of any
|
||||
* kind, whether express or implied.
|
||||
*/
|
||||
|
||||
#include <linux/err.h>
|
||||
#include <linux/kernel.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/errno.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/i2c.h>
|
||||
#include <linux/interrupt.h>
|
||||
#include <linux/wait.h>
|
||||
#include <linux/slab.h>
|
||||
#include <linux/io.h>
|
||||
#include <linux/log2.h>
|
||||
#include <linux/hwmon.h>
|
||||
#include <linux/hwmon-sysfs.h>
|
||||
#include <fpga_i2c_ocores.h>
|
||||
#include <linux/spinlock.h>
|
||||
#include <linux/delay.h>
|
||||
|
||||
|
||||
struct ocores_i2c {
|
||||
void __iomem *base;
|
||||
u32 reg_shift;
|
||||
u32 reg_io_width;
|
||||
wait_queue_head_t wait;
|
||||
struct i2c_adapter adap;
|
||||
struct i2c_msg *msg;
|
||||
int pos;
|
||||
int nmsgs;
|
||||
int state; /* see STATE_ */
|
||||
spinlock_t process_lock;
|
||||
struct mutex xfer_lock;
|
||||
int clock_khz;
|
||||
void (*setreg)(struct ocores_i2c *i2c, int reg, u8 value);
|
||||
u8 (*getreg)(struct ocores_i2c *i2c, int reg);
|
||||
};
|
||||
|
||||
/* registers */
|
||||
#define OCI2C_PRELOW 0x0
|
||||
#define OCI2C_PREHIGH 0x4
|
||||
#define OCI2C_CONTROL 0x8
|
||||
#define OCI2C_DATA 0xc
|
||||
#define OCI2C_CMD 0x10 /* write only */
|
||||
#define OCI2C_STATUS 0x10 /* read only, same address as OCI2C_CMD */
|
||||
|
||||
#define OCI2C_TRAN_REV 0x14
|
||||
#define OCI2C_CMD_REV 0x18
|
||||
|
||||
|
||||
#define OCI2C_CTRL_IEN 0x40
|
||||
#define OCI2C_CTRL_EN 0x80
|
||||
|
||||
#define OCI2C_CMD_START 0x91
|
||||
#define OCI2C_CMD_STOP 0x41
|
||||
#define OCI2C_CMD_READ 0x21
|
||||
#define OCI2C_CMD_WRITE 0x11
|
||||
#define OCI2C_CMD_READ_ACK 0x21
|
||||
#define OCI2C_CMD_READ_NACK 0x29
|
||||
#define OCI2C_CMD_IACK 0x01
|
||||
|
||||
#define OCI2C_STAT_IF 0x01
|
||||
#define OCI2C_STAT_TIP 0x02
|
||||
#define OCI2C_STAT_ARBLOST 0x20
|
||||
#define OCI2C_STAT_BUSY 0x40
|
||||
#define OCI2C_STAT_NACK 0x80
|
||||
|
||||
#define STATE_DONE 0
|
||||
#define STATE_START 1
|
||||
#define STATE_WRITE 2
|
||||
#define STATE_READ 3
|
||||
#define STATE_ERROR 4
|
||||
|
||||
#define TYPE_OCORES 0
|
||||
#define TYPE_GRLIB 1
|
||||
|
||||
#define BUF_SIZE 256
|
||||
#define DEFAULT_I2C_SCL 100
|
||||
#define DEFAULT_I2C_PRE 0xF9
|
||||
|
||||
int g_fpga_i2c_debug = 0;
|
||||
int g_fpga_i2c_irq = 0;
|
||||
int g_fpga_i2c_error = 0;
|
||||
int g_irq_dump_debug = 0;
|
||||
int g_irq_invalid_cnt = 0;
|
||||
int g_fpga_debug = 0;
|
||||
|
||||
module_param(g_fpga_i2c_debug, int, S_IRUGO | S_IWUSR);
|
||||
module_param(g_fpga_i2c_error, int, S_IRUGO | S_IWUSR);
|
||||
module_param(g_fpga_i2c_irq, int, S_IRUGO | S_IWUSR);
|
||||
module_param(g_irq_dump_debug, int, S_IRUGO | S_IWUSR);
|
||||
module_param(g_irq_invalid_cnt, int, S_IRUGO | S_IWUSR);
|
||||
module_param(g_fpga_debug, int, S_IRUGO | S_IWUSR);
|
||||
|
||||
#define FPGA_I2C_DEBUG(fmt, args...) do { \
|
||||
if (g_fpga_debug) { \
|
||||
printk(KERN_DEBUG ""fmt, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define FPGA_I2C_DEBUG_DUMP(fmt, args...) do { \
|
||||
if (g_irq_dump_debug) { \
|
||||
printk(KERN_ERR ""fmt, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define FPGA_I2C_DEBUG_XFER(fmt, args...) do { \
|
||||
if (g_fpga_i2c_irq) { \
|
||||
printk(KERN_ERR "[FPGA_I2C][XFER][func:%s line:%d]\r\n"fmt, __func__, __LINE__, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define FPGA_I2C_DEBUG_VERBOSE(fmt, args...) do { \
|
||||
if (g_fpga_i2c_debug) { \
|
||||
printk(KERN_ERR "[FPGA_I2C][VER][func:%s line:%d]\r\n"fmt, __func__, __LINE__, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define FPGA_I2C_DEBUG_ERROR(fmt, args...) do { \
|
||||
if (g_fpga_i2c_error) { \
|
||||
printk(KERN_ERR "[FPGA_I2C][ERR][func:%s line:%d]\r\n"fmt, __func__, __LINE__, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
static int check_ocores_i2c(struct i2c_msg *msgs, int num);
|
||||
static void oc_debug_dump_reg(struct ocores_i2c *i2c);
|
||||
static void oc_debug_dump_reg_dump(struct ocores_i2c *i2c);
|
||||
static int oc_set_scl_clk(struct ocores_i2c *i2c, int val);
|
||||
|
||||
static void oc_setreg_8(struct ocores_i2c *i2c, int reg, u8 value)
|
||||
{
|
||||
iowrite8(value, i2c->base + (reg << i2c->reg_shift));
|
||||
}
|
||||
|
||||
static void oc_setreg_16(struct ocores_i2c *i2c, int reg, u8 value)
|
||||
{
|
||||
iowrite16(value, i2c->base + (reg << i2c->reg_shift));
|
||||
}
|
||||
|
||||
static void oc_setreg_32(struct ocores_i2c *i2c, int reg, u8 value)
|
||||
{
|
||||
iowrite32(value, i2c->base + (reg << i2c->reg_shift));
|
||||
}
|
||||
|
||||
static inline u8 oc_getreg_8(struct ocores_i2c *i2c, int reg)
|
||||
{
|
||||
return ioread8(i2c->base + (reg << i2c->reg_shift));
|
||||
}
|
||||
|
||||
static inline u8 oc_getreg_16(struct ocores_i2c *i2c, int reg)
|
||||
{
|
||||
return ioread16(i2c->base + (reg << i2c->reg_shift));
|
||||
}
|
||||
|
||||
static inline u8 oc_getreg_32(struct ocores_i2c *i2c, int reg)
|
||||
{
|
||||
return ioread32(i2c->base + (reg << i2c->reg_shift));
|
||||
}
|
||||
|
||||
static inline void oc_setreg(struct ocores_i2c *i2c, int reg, u8 value)
|
||||
{
|
||||
i2c->setreg(i2c, reg, value);
|
||||
}
|
||||
|
||||
static inline u8 oc_getreg(struct ocores_i2c *i2c, int reg)
|
||||
{
|
||||
return i2c->getreg(i2c, reg);
|
||||
}
|
||||
|
||||
#define FPGA_I2C_SPIN_LOCK(lock, flags) spin_lock_irqsave(&(lock), (flags))
|
||||
#define FPGA_I2C_SPIN_UNLOCK(lock, flags) spin_unlock_irqrestore(&(lock), (flags))
|
||||
#define FPGA_I2C_MUTEX_LOCK(lock) mutex_lock(&(lock))
|
||||
#define FPGA_I2C_MUTEX_UNLOCK(lock) mutex_unlock(&(lock))
|
||||
|
||||
static void ocores_process(struct ocores_i2c *i2c, u8 stat)
|
||||
{
|
||||
struct i2c_msg *msg = i2c->msg;
|
||||
|
||||
FPGA_I2C_DEBUG_XFER("Enter nr %d.\n", i2c->adap.nr);
|
||||
if ((i2c->state == STATE_DONE) || (i2c->state == STATE_ERROR)) {
|
||||
/* stop has been sent */
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_IACK);
|
||||
wake_up(&i2c->wait);
|
||||
FPGA_I2C_DEBUG_XFER("stop has been sent, exit.\n");
|
||||
goto out;
|
||||
}
|
||||
|
||||
FPGA_I2C_DEBUG_XFER("Enter 111.\n");
|
||||
|
||||
/* error */
|
||||
if (stat & OCI2C_STAT_ARBLOST) {
|
||||
i2c->state = STATE_ERROR;
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_STOP);
|
||||
FPGA_I2C_DEBUG_XFER("error, exit.\n");
|
||||
goto out;
|
||||
}
|
||||
|
||||
FPGA_I2C_DEBUG_XFER("Enter 222.\n");
|
||||
|
||||
if (check_ocores_i2c(i2c->msg, i2c->nmsgs) != 0) {
|
||||
FPGA_I2C_DEBUG("i2c->msg->buf is null, i2c->state:%d exit.\n", i2c->state);
|
||||
oc_debug_dump_reg_dump(i2c);
|
||||
i2c->state = STATE_ERROR;
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_STOP);
|
||||
goto out;
|
||||
}
|
||||
|
||||
if ((i2c->state == STATE_START) || (i2c->state == STATE_WRITE)) {
|
||||
i2c->state =
|
||||
(msg->flags & I2C_M_RD) ? STATE_READ : STATE_WRITE;
|
||||
|
||||
if (stat & OCI2C_STAT_NACK) {
|
||||
i2c->state = STATE_ERROR;
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_STOP);
|
||||
FPGA_I2C_DEBUG_XFER("OCI2C_STAT_NACK, exit.\n");
|
||||
goto out;
|
||||
}
|
||||
} else {
|
||||
msg->buf[i2c->pos++] = oc_getreg(i2c, OCI2C_DATA);
|
||||
}
|
||||
FPGA_I2C_DEBUG_XFER("Enter 333.\n");
|
||||
|
||||
/* end of msg? */
|
||||
if (i2c->pos == msg->len) {
|
||||
FPGA_I2C_DEBUG_XFER("Enter end of msg.\n");
|
||||
i2c->nmsgs--;
|
||||
i2c->msg++;
|
||||
i2c->pos = 0;
|
||||
msg = i2c->msg;
|
||||
|
||||
if (i2c->nmsgs) { /* end? */
|
||||
/* send start? */
|
||||
if (!(msg->flags & I2C_M_NOSTART)) {
|
||||
u8 addr = (msg->addr << 1);
|
||||
|
||||
if (msg->flags & I2C_M_RD)
|
||||
addr |= 1;
|
||||
|
||||
i2c->state = STATE_START;
|
||||
|
||||
oc_setreg(i2c, OCI2C_DATA, addr);
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_START);
|
||||
FPGA_I2C_DEBUG_XFER("send start, exit.\n");
|
||||
goto out;
|
||||
}
|
||||
|
||||
i2c->state = (msg->flags & I2C_M_RD)
|
||||
? STATE_READ : STATE_WRITE;
|
||||
} else {
|
||||
i2c->state = STATE_DONE;
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_STOP);
|
||||
FPGA_I2C_DEBUG_XFER("send OCI2C_CMD_STOP, exit.\n");
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
|
||||
if (i2c->state == STATE_READ) {
|
||||
oc_setreg(i2c, OCI2C_CMD, i2c->pos == (msg->len-1) ?
|
||||
OCI2C_CMD_READ_NACK : OCI2C_CMD_READ_ACK);
|
||||
} else {
|
||||
oc_setreg(i2c, OCI2C_DATA, msg->buf[i2c->pos++]);
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_WRITE);
|
||||
}
|
||||
|
||||
out:
|
||||
FPGA_I2C_DEBUG_XFER("normal, exit nr %d.\n", i2c->adap.nr);
|
||||
}
|
||||
|
||||
static irqreturn_t ocores_isr(int irq, void *dev_id)
|
||||
{
|
||||
struct ocores_i2c *i2c = dev_id;
|
||||
unsigned long flags;
|
||||
u8 stat;
|
||||
|
||||
if (!i2c) {
|
||||
return IRQ_NONE;
|
||||
}
|
||||
/*
|
||||
* If we spin here is because we are in timeout, so we are going
|
||||
* to be in STATE_ERROR. See ocores_process_timeout()
|
||||
*/
|
||||
FPGA_I2C_SPIN_LOCK(i2c->process_lock, flags);
|
||||
stat = oc_getreg(i2c, OCI2C_STATUS);
|
||||
if (!(stat & OCI2C_STAT_IF)) {
|
||||
g_irq_invalid_cnt++;
|
||||
FPGA_I2C_SPIN_UNLOCK(i2c->process_lock, flags);
|
||||
return IRQ_NONE;
|
||||
}
|
||||
|
||||
FPGA_I2C_DEBUG_XFER("Enter, irq %d nr %d addr 0x%x.\n", irq, i2c->adap.nr, (!i2c->msg)?0:i2c->msg->addr);
|
||||
ocores_process(i2c, stat);
|
||||
FPGA_I2C_DEBUG_XFER("Leave, irq %d nr %d addr 0x%x.\n", irq, i2c->adap.nr, (!i2c->msg)?0:i2c->msg->addr);
|
||||
|
||||
FPGA_I2C_SPIN_UNLOCK(i2c->process_lock, flags);
|
||||
return IRQ_HANDLED;
|
||||
}
|
||||
|
||||
/**
|
||||
* Process timeout event
|
||||
* @i2c: ocores I2C device instance
|
||||
*/
|
||||
static void ocores_process_timeout(struct ocores_i2c *i2c)
|
||||
{
|
||||
unsigned long flags;
|
||||
|
||||
FPGA_I2C_SPIN_LOCK(i2c->process_lock, flags);
|
||||
FPGA_I2C_DEBUG_ERROR("wait_event_timeout i2c->state %d.\n", i2c->state);
|
||||
oc_debug_dump_reg(i2c);
|
||||
i2c->state = STATE_ERROR;
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_STOP);
|
||||
mdelay(1);
|
||||
FPGA_I2C_SPIN_UNLOCK(i2c->process_lock, flags);
|
||||
}
|
||||
|
||||
static int check_ocores_i2c(struct i2c_msg *msgs, int num)
|
||||
{
|
||||
int i;
|
||||
if (!msgs) {
|
||||
return -1;
|
||||
}
|
||||
for (i = 0; i < num; ++i) {
|
||||
if (!msgs[i].buf) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int ocores_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num)
|
||||
{
|
||||
struct ocores_i2c *i2c;
|
||||
int ret;
|
||||
unsigned long flags;
|
||||
int xfer_ret;
|
||||
|
||||
if (!adap || check_ocores_i2c(msgs, num) != 0) {
|
||||
FPGA_I2C_DEBUG("msgs: %p , num:%d exit.\n", msgs, num);
|
||||
return -EINVAL;
|
||||
}
|
||||
i2c = i2c_get_adapdata(adap);
|
||||
|
||||
FPGA_I2C_MUTEX_LOCK(i2c->xfer_lock);
|
||||
FPGA_I2C_SPIN_LOCK(i2c->process_lock, flags);
|
||||
i2c->msg = msgs;
|
||||
i2c->pos = 0;
|
||||
i2c->nmsgs = num;
|
||||
i2c->state = STATE_START;
|
||||
FPGA_I2C_DEBUG_XFER("Enter, nr %d addr 0x%x num %d.\n", adap->nr, i2c->msg->addr, num);
|
||||
|
||||
oc_setreg(i2c, OCI2C_DATA,
|
||||
(i2c->msg->addr << 1) |
|
||||
((i2c->msg->flags & I2C_M_RD) ? 1:0));
|
||||
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_START);
|
||||
FPGA_I2C_DEBUG_XFER("After, oc_setreg OCI2C_CMD.\n");
|
||||
FPGA_I2C_SPIN_UNLOCK(i2c->process_lock, flags);
|
||||
|
||||
ret = wait_event_timeout(i2c->wait, (i2c->state == STATE_ERROR) ||
|
||||
(i2c->state == STATE_DONE), HZ);
|
||||
|
||||
if (ret == 0) {
|
||||
ocores_process_timeout(i2c);
|
||||
FPGA_I2C_MUTEX_UNLOCK(i2c->xfer_lock);
|
||||
return -ETIMEDOUT;
|
||||
}
|
||||
xfer_ret = i2c->state;
|
||||
FPGA_I2C_MUTEX_UNLOCK(i2c->xfer_lock);
|
||||
return (xfer_ret == STATE_DONE) ? num : -EIO;
|
||||
}
|
||||
|
||||
static void ocores_init(struct ocores_i2c *i2c)
|
||||
{
|
||||
int prescale;
|
||||
u8 ctrl = oc_getreg(i2c, OCI2C_CONTROL);
|
||||
|
||||
mutex_init(&i2c->xfer_lock);
|
||||
spin_lock_init(&i2c->process_lock);
|
||||
|
||||
/* make sure the device is disabled */
|
||||
oc_setreg(i2c, OCI2C_CONTROL, ctrl & ~(OCI2C_CTRL_EN|OCI2C_CTRL_IEN));
|
||||
|
||||
prescale = oc_set_scl_clk(i2c, DEFAULT_I2C_SCL);
|
||||
FPGA_I2C_DEBUG_VERBOSE("i2c->base 0x%p, i2c->clock_khz %d, prescale 0x%x.\n", i2c->base, i2c->clock_khz, prescale);
|
||||
|
||||
/* Init the device */
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_IACK);
|
||||
oc_setreg(i2c, OCI2C_CONTROL, ctrl | OCI2C_CTRL_IEN | OCI2C_CTRL_EN);
|
||||
}
|
||||
|
||||
|
||||
static u32 ocores_func(struct i2c_adapter *adap)
|
||||
{
|
||||
return I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL;
|
||||
}
|
||||
|
||||
static const struct i2c_algorithm ocores_algorithm = {
|
||||
.master_xfer = ocores_xfer,
|
||||
.functionality = ocores_func,
|
||||
};
|
||||
|
||||
static struct i2c_adapter ocores_adapter = {
|
||||
.owner = THIS_MODULE,
|
||||
.name = "rg-i2c-ocores",
|
||||
.class = I2C_CLASS_HWMON | I2C_CLASS_SPD | I2C_CLASS_DEPRECATED,
|
||||
.algo = &ocores_algorithm,
|
||||
};
|
||||
|
||||
static const struct of_device_id ocores_i2c_match[] = {
|
||||
{
|
||||
.compatible = "opencores,rg-i2c-ocores",
|
||||
.data = (void *)TYPE_OCORES,
|
||||
},
|
||||
{
|
||||
.compatible = "aeroflexgaisler,i2cmst",
|
||||
.data = (void *)TYPE_GRLIB,
|
||||
},
|
||||
{},
|
||||
};
|
||||
MODULE_DEVICE_TABLE(of, ocores_i2c_match);
|
||||
|
||||
#ifdef CONFIG_OF
|
||||
/* Read and write functions for the GRLIB port of the controller. Registers are
|
||||
* 32-bit big endian and the PRELOW and PREHIGH registers are merged into one
|
||||
* register. The subsequent registers has their offset decreased accordingly. */
|
||||
static u8 oc_getreg_grlib(struct ocores_i2c *i2c, int reg)
|
||||
{
|
||||
u32 rd;
|
||||
int rreg = reg;
|
||||
if (reg != OCI2C_PRELOW)
|
||||
rreg--;
|
||||
rd = ioread32be(i2c->base + (rreg << i2c->reg_shift));
|
||||
if (reg == OCI2C_PREHIGH)
|
||||
return (u8)(rd >> 8);
|
||||
else
|
||||
return (u8)rd;
|
||||
}
|
||||
|
||||
static void oc_setreg_grlib(struct ocores_i2c *i2c, int reg, u8 value)
|
||||
{
|
||||
u32 curr, wr;
|
||||
int rreg = reg;
|
||||
if (reg != OCI2C_PRELOW)
|
||||
rreg--;
|
||||
if (reg == OCI2C_PRELOW || reg == OCI2C_PREHIGH) {
|
||||
curr = ioread32be(i2c->base + (rreg << i2c->reg_shift));
|
||||
if (reg == OCI2C_PRELOW)
|
||||
wr = (curr & 0xff00) | value;
|
||||
else
|
||||
wr = (((u32)value) << 8) | (curr & 0xff);
|
||||
} else {
|
||||
wr = value;
|
||||
}
|
||||
iowrite32be(wr, i2c->base + (rreg << i2c->reg_shift));
|
||||
}
|
||||
|
||||
static int ocores_i2c_of_probe(struct platform_device *pdev,
|
||||
struct ocores_i2c *i2c)
|
||||
{
|
||||
struct device_node *np = pdev->dev.of_node;
|
||||
const struct of_device_id *match;
|
||||
u32 val;
|
||||
|
||||
if (of_property_read_u32(np, "reg-shift", &i2c->reg_shift)) {
|
||||
/* no 'reg-shift', check for deprecated 'regstep' */
|
||||
if (!of_property_read_u32(np, "regstep", &val)) {
|
||||
if (!is_power_of_2(val)) {
|
||||
dev_err(&pdev->dev, "invalid regstep %d\n",
|
||||
val);
|
||||
return -EINVAL;
|
||||
}
|
||||
i2c->reg_shift = ilog2(val);
|
||||
dev_warn(&pdev->dev,
|
||||
"regstep property deprecated, use reg-shift\n");
|
||||
}
|
||||
}
|
||||
|
||||
if (of_property_read_u32(np, "clock-frequency", &val)) {
|
||||
dev_err(&pdev->dev,
|
||||
"Missing required parameter 'clock-frequency'\n");
|
||||
return -ENODEV;
|
||||
}
|
||||
i2c->clock_khz = val / 1000;
|
||||
|
||||
of_property_read_u32(pdev->dev.of_node, "reg-io-width",
|
||||
&i2c->reg_io_width);
|
||||
|
||||
match = of_match_node(ocores_i2c_match, pdev->dev.of_node);
|
||||
if (match && (long)match->data == TYPE_GRLIB) {
|
||||
dev_dbg(&pdev->dev, "GRLIB variant of i2c-ocores\n");
|
||||
i2c->setreg = oc_setreg_grlib;
|
||||
i2c->getreg = oc_getreg_grlib;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
#else
|
||||
#define ocores_i2c_of_probe(pdev,i2c) -ENODEV
|
||||
#endif
|
||||
|
||||
|
||||
static void oc_debug_dump_reg_dump(struct ocores_i2c *i2c)
|
||||
{
|
||||
if (i2c) {
|
||||
FPGA_I2C_DEBUG("base: %p.\n", i2c->base);
|
||||
FPGA_I2C_DEBUG("reg_shift: %d.\n", i2c->reg_shift);
|
||||
FPGA_I2C_DEBUG("reg_io_width: %d.\n", i2c->reg_io_width);
|
||||
FPGA_I2C_DEBUG("adap.nr: %d.\n", i2c->adap.nr);
|
||||
FPGA_I2C_DEBUG("msg: %p.\n", i2c->msg);
|
||||
if (i2c->msg) {
|
||||
FPGA_I2C_DEBUG("msg->buf: %p.\n", i2c->msg->buf);
|
||||
FPGA_I2C_DEBUG("msg->addr: 0x%x.\n", i2c->msg->addr);
|
||||
FPGA_I2C_DEBUG("msg->flags: 0x%x.\n", i2c->msg->flags);
|
||||
FPGA_I2C_DEBUG("msg->len: %d.\n", i2c->msg->len);
|
||||
} else {
|
||||
FPGA_I2C_DEBUG("msg: %p is null.\n", i2c->msg);
|
||||
}
|
||||
|
||||
FPGA_I2C_DEBUG("pos: %d.\n", i2c->pos);
|
||||
FPGA_I2C_DEBUG("nmsgs: %d.\n", i2c->nmsgs);
|
||||
FPGA_I2C_DEBUG("state: %d.\n", i2c->state);
|
||||
FPGA_I2C_DEBUG("clock_khz: %d.\n", i2c->clock_khz);
|
||||
FPGA_I2C_DEBUG("setreg: %p.\n", i2c->setreg);
|
||||
FPGA_I2C_DEBUG("getreg: %p.\n", i2c->getreg);
|
||||
if (i2c->getreg) {
|
||||
FPGA_I2C_DEBUG("OCI2C_PRELOW: 0x%02x.\n", oc_getreg(i2c, OCI2C_PRELOW));
|
||||
FPGA_I2C_DEBUG("OCI2C_PREHIGH: 0x%02x.\n", oc_getreg(i2c, OCI2C_PREHIGH));
|
||||
FPGA_I2C_DEBUG("OCI2C_CONTROL: 0x%02x.\n", oc_getreg(i2c, OCI2C_CONTROL));
|
||||
FPGA_I2C_DEBUG("OCI2C_DATA: 0x%02x.\n", oc_getreg(i2c, OCI2C_DATA));
|
||||
FPGA_I2C_DEBUG("OCI2C_CMD: 0x%02x.\n", oc_getreg(i2c, OCI2C_CMD));
|
||||
FPGA_I2C_DEBUG("OCI2C_STATUS: 0x%02x.\n", oc_getreg(i2c, OCI2C_STATUS));
|
||||
} else {
|
||||
FPGA_I2C_DEBUG("getreg: %p is null.\n", i2c->getreg);
|
||||
}
|
||||
} else {
|
||||
FPGA_I2C_DEBUG("i2c %p is null.\n", i2c);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void oc_debug_dump_reg(struct ocores_i2c *i2c)
|
||||
{
|
||||
if (i2c) {
|
||||
FPGA_I2C_DEBUG_DUMP("base: %p.\n", i2c->base);
|
||||
FPGA_I2C_DEBUG_DUMP("reg_shift: %d.\n", i2c->reg_shift);
|
||||
FPGA_I2C_DEBUG_DUMP("reg_io_width: %d.\n", i2c->reg_io_width);
|
||||
FPGA_I2C_DEBUG_DUMP("adap.nr: %d.\n", i2c->adap.nr);
|
||||
FPGA_I2C_DEBUG_DUMP("msg: %p.\n", i2c->msg);
|
||||
if (i2c->msg) {
|
||||
FPGA_I2C_DEBUG_DUMP("msg->buf: %p.\n", i2c->msg->buf);
|
||||
FPGA_I2C_DEBUG_DUMP("msg->addr: 0x%x.\n", i2c->msg->addr);
|
||||
FPGA_I2C_DEBUG_DUMP("msg->flags: 0x%x.\n", i2c->msg->flags);
|
||||
FPGA_I2C_DEBUG_DUMP("msg->len: %d.\n", i2c->msg->len);
|
||||
} else {
|
||||
FPGA_I2C_DEBUG_DUMP("msg: %p is null.\n", i2c->msg);
|
||||
}
|
||||
|
||||
FPGA_I2C_DEBUG_DUMP("pos: %d.\n", i2c->pos);
|
||||
FPGA_I2C_DEBUG_DUMP("nmsgs: %d.\n", i2c->nmsgs);
|
||||
FPGA_I2C_DEBUG_DUMP("state: %d.\n", i2c->state);
|
||||
FPGA_I2C_DEBUG_DUMP("clock_khz: %d.\n", i2c->clock_khz);
|
||||
FPGA_I2C_DEBUG_DUMP("setreg: %p.\n", i2c->setreg);
|
||||
FPGA_I2C_DEBUG_DUMP("getreg: %p.\n", i2c->getreg);
|
||||
if (i2c->getreg) {
|
||||
FPGA_I2C_DEBUG_DUMP("OCI2C_PRELOW: 0x%02x.\n", oc_getreg(i2c, OCI2C_PRELOW));
|
||||
FPGA_I2C_DEBUG_DUMP("OCI2C_PREHIGH: 0x%02x.\n", oc_getreg(i2c, OCI2C_PREHIGH));
|
||||
FPGA_I2C_DEBUG_DUMP("OCI2C_CONTROL: 0x%02x.\n", oc_getreg(i2c, OCI2C_CONTROL));
|
||||
FPGA_I2C_DEBUG_DUMP("OCI2C_DATA: 0x%02x.\n", oc_getreg(i2c, OCI2C_DATA));
|
||||
FPGA_I2C_DEBUG_DUMP("OCI2C_CMD: 0x%02x.\n", oc_getreg(i2c, OCI2C_CMD));
|
||||
FPGA_I2C_DEBUG_DUMP("OCI2C_STATUS: 0x%02x.\n", oc_getreg(i2c, OCI2C_STATUS));
|
||||
} else {
|
||||
FPGA_I2C_DEBUG_DUMP("getreg: %p is null.\n", i2c->getreg);
|
||||
}
|
||||
} else {
|
||||
FPGA_I2C_DEBUG_DUMP("i2c %p is null.\n", i2c);
|
||||
}
|
||||
}
|
||||
|
||||
void oc_debug_dump_reg_exception(void)
|
||||
{
|
||||
int bus_beg, bus_end, bus;
|
||||
struct i2c_adapter *adap;
|
||||
struct ocores_i2c *adap_data;
|
||||
|
||||
bus_beg = 1;
|
||||
bus_end = 14;
|
||||
for (bus = bus_beg; bus <= bus_end; bus++) {
|
||||
adap = i2c_get_adapter(bus);
|
||||
if (adap) {
|
||||
adap_data = (struct ocores_i2c *)i2c_get_adapdata(adap);
|
||||
if (adap_data) {
|
||||
FPGA_I2C_DEBUG_DUMP("bus %d call oc_debug_dump_reg begin.\n", bus);
|
||||
oc_debug_dump_reg(adap_data);
|
||||
FPGA_I2C_DEBUG_DUMP("bus %d call oc_debug_dump_reg end.\n", bus);
|
||||
} else {
|
||||
FPGA_I2C_DEBUG_DUMP("bus %d i2c_get_adapdata null.\n", bus);
|
||||
}
|
||||
i2c_put_adapter(adap);
|
||||
} else {
|
||||
FPGA_I2C_DEBUG_DUMP("bus %d i2c_get_adapter null.\n", bus);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static int oc_calculate_prescale(struct ocores_i2c *i2c, int val) {
|
||||
if (val <= 0) {
|
||||
FPGA_I2C_DEBUG_ERROR("input scl clock error, set to default clock: %d.\n", val);
|
||||
val = DEFAULT_I2C_SCL;
|
||||
}
|
||||
return (i2c->clock_khz / (5 * val)) - 1;
|
||||
}
|
||||
|
||||
static int oc_calculate_scl_clk(struct ocores_i2c *i2c, int prescale) {
|
||||
if (prescale <= -1) {
|
||||
FPGA_I2C_DEBUG_ERROR("input prescale error, set to default prescale: %d.\n", prescale);
|
||||
prescale = DEFAULT_I2C_PRE;
|
||||
}
|
||||
return (i2c->clock_khz / (prescale + 1)) / 5;
|
||||
}
|
||||
|
||||
static int oc_set_scl_clk(struct ocores_i2c *i2c, int val) {
|
||||
int prescale;
|
||||
|
||||
prescale = oc_calculate_prescale(i2c, val);
|
||||
oc_setreg(i2c, OCI2C_PRELOW, prescale & 0xff);
|
||||
oc_setreg(i2c, OCI2C_PREHIGH, prescale >> 8);
|
||||
return prescale;
|
||||
}
|
||||
|
||||
static int oc_get_scl_clk(struct ocores_i2c *i2c) {
|
||||
int prescale, prescale_high, prescale_low;
|
||||
|
||||
prescale_low = oc_getreg(i2c, OCI2C_PRELOW);
|
||||
prescale_high = oc_getreg(i2c, OCI2C_PREHIGH);
|
||||
prescale = (prescale_high << 8) + (prescale_low & 0xff);
|
||||
|
||||
return oc_calculate_scl_clk(i2c, prescale);
|
||||
}
|
||||
|
||||
static ssize_t oc_sysfs_show_scl_clk(struct device *dev, struct device_attribute *attr, char *buf)
|
||||
{
|
||||
struct i2c_adapter *adapter;
|
||||
struct ocores_i2c *i2c;
|
||||
int scl_clk;
|
||||
|
||||
adapter = to_i2c_adapter(dev);
|
||||
i2c = (struct ocores_i2c *)i2c_get_adapdata(adapter);
|
||||
scl_clk = oc_get_scl_clk(i2c);
|
||||
return snprintf(buf, BUF_SIZE, "%d\n", scl_clk);
|
||||
}
|
||||
|
||||
static ssize_t oc_sysfs_set_scl_clk(struct device *dev, struct device_attribute *attr, const char *buf, size_t count)
|
||||
{
|
||||
struct i2c_adapter *adapter;
|
||||
struct ocores_i2c *i2c;
|
||||
int val;
|
||||
int ret;
|
||||
int prescale;
|
||||
|
||||
adapter = to_i2c_adapter(dev);
|
||||
i2c = (struct ocores_i2c *)i2c_get_adapdata(adapter);
|
||||
ret = kstrtoint(buf, 0, &val);
|
||||
if (ret) {
|
||||
return ret;
|
||||
}
|
||||
FPGA_I2C_MUTEX_LOCK(i2c->xfer_lock);
|
||||
prescale = oc_set_scl_clk(i2c, val);
|
||||
FPGA_I2C_DEBUG_VERBOSE("i2c->base 0x%p, i2c->clock_khz %d, scl clk 0x%x.\n", i2c->base, i2c->clock_khz, prescale);
|
||||
FPGA_I2C_MUTEX_UNLOCK(i2c->xfer_lock);
|
||||
return count;
|
||||
}
|
||||
static ssize_t show_oc_debug_value(struct device *dev, struct device_attribute *da, char *buf)
|
||||
{
|
||||
oc_debug_dump_reg_exception();
|
||||
return 0;
|
||||
}
|
||||
|
||||
static SENSOR_DEVICE_ATTR(oc_debug, S_IRUGO | S_IWUSR, show_oc_debug_value, NULL, 0x15);
|
||||
static SENSOR_DEVICE_ATTR(oc_scl_clk, S_IRUGO | S_IWUSR, oc_sysfs_show_scl_clk, oc_sysfs_set_scl_clk, 0);
|
||||
|
||||
static struct attribute *oc_debug_sysfs_attrs[] = {
|
||||
&sensor_dev_attr_oc_debug.dev_attr.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
static struct attribute *oc_scl_clk_sysfs_attrs[] = {
|
||||
&sensor_dev_attr_oc_scl_clk.dev_attr.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
static const struct attribute_group oc_debug_sysfs_group = {
|
||||
.attrs = oc_debug_sysfs_attrs,
|
||||
};
|
||||
|
||||
static const struct attribute_group oc_scl_clk_sysfs_group = {
|
||||
.attrs = oc_scl_clk_sysfs_attrs,
|
||||
};
|
||||
|
||||
static void oc_scl_clk_sysfs_init(struct i2c_adapter *adap)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret = sysfs_create_group(&adap->dev.kobj, &oc_scl_clk_sysfs_group);
|
||||
FPGA_I2C_DEBUG_VERBOSE("sysfs_create_group ret %d.\n", ret);
|
||||
return;
|
||||
}
|
||||
|
||||
static void oc_scl_clk_sysfs_exit(struct i2c_adapter *adap)
|
||||
{
|
||||
sysfs_remove_group(&adap->dev.kobj, (const struct attribute_group *)&oc_scl_clk_sysfs_group);
|
||||
FPGA_I2C_DEBUG_VERBOSE("sysfs_remove_group.\n");
|
||||
return;
|
||||
}
|
||||
|
||||
static void oc_debug_sysfs_init(struct platform_device *pdev)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret = sysfs_create_group(&pdev->dev.kobj, &oc_debug_sysfs_group);
|
||||
FPGA_I2C_DEBUG_VERBOSE("sysfs_create_group ret %d.\n", ret);
|
||||
return;
|
||||
}
|
||||
|
||||
static void oc_debug_sysfs_exit(struct platform_device *pdev)
|
||||
{
|
||||
sysfs_remove_group(&pdev->dev.kobj, (const struct attribute_group *)&oc_debug_sysfs_group);
|
||||
FPGA_I2C_DEBUG_VERBOSE("sysfs_remove_group.\n");
|
||||
return;
|
||||
}
|
||||
|
||||
static int rg_ocores_i2c_probe(struct platform_device *pdev)
|
||||
{
|
||||
struct ocores_i2c *i2c;
|
||||
struct rg_ocores_i2c_platform_data *pdata;
|
||||
struct resource *res;
|
||||
int irq;
|
||||
int ret;
|
||||
int i;
|
||||
|
||||
FPGA_I2C_DEBUG_VERBOSE("Enter.\n");
|
||||
irq = platform_get_irq(pdev, 0);
|
||||
if (irq < 0) {
|
||||
FPGA_I2C_DEBUG_ERROR("platform_get_irq failed irq %d.\n", irq);
|
||||
return irq;
|
||||
}
|
||||
|
||||
i2c = devm_kzalloc(&pdev->dev, sizeof(*i2c), GFP_KERNEL);
|
||||
if (!i2c) {
|
||||
FPGA_I2C_DEBUG_ERROR("devm_kzalloc failed.\n");
|
||||
return -ENOMEM;
|
||||
}
|
||||
res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
|
||||
i2c->base = devm_ioremap_resource(&pdev->dev, res);
|
||||
if (IS_ERR(i2c->base)) {
|
||||
FPGA_I2C_DEBUG_ERROR("devm_ioremap_resource failed.\n");
|
||||
return PTR_ERR(i2c->base);
|
||||
}
|
||||
|
||||
pdata = dev_get_platdata(&pdev->dev);
|
||||
if (pdata) {
|
||||
i2c->reg_shift = pdata->reg_shift;
|
||||
i2c->reg_io_width = pdata->reg_io_width;
|
||||
i2c->clock_khz = pdata->clock_khz;
|
||||
} else {
|
||||
ret = ocores_i2c_of_probe(pdev, i2c);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (i2c->reg_io_width == 0)
|
||||
i2c->reg_io_width = 1; /* Set to default value */
|
||||
|
||||
|
||||
if (!i2c->setreg || !i2c->getreg) {
|
||||
switch (i2c->reg_io_width) {
|
||||
case 1:
|
||||
i2c->setreg = oc_setreg_8;
|
||||
i2c->getreg = oc_getreg_8;
|
||||
break;
|
||||
|
||||
case 2:
|
||||
i2c->setreg = oc_setreg_16;
|
||||
i2c->getreg = oc_getreg_16;
|
||||
break;
|
||||
|
||||
case 4:
|
||||
i2c->setreg = oc_setreg_32;
|
||||
i2c->getreg = oc_getreg_32;
|
||||
break;
|
||||
|
||||
default:
|
||||
dev_err(&pdev->dev, "Unsupported I/O width (%d)\n",
|
||||
i2c->reg_io_width);
|
||||
return -EINVAL;
|
||||
}
|
||||
}
|
||||
|
||||
ocores_init(i2c);
|
||||
|
||||
init_waitqueue_head(&i2c->wait);
|
||||
ret = devm_request_irq(&pdev->dev, irq, ocores_isr, 0,
|
||||
pdev->name, i2c);
|
||||
if (ret) {
|
||||
dev_err(&pdev->dev, "Cannot claim IRQ\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* hook up driver to tree */
|
||||
platform_set_drvdata(pdev, i2c);
|
||||
i2c->adap = ocores_adapter;
|
||||
if (pdata->nr) {
|
||||
i2c->adap.nr = pdata->nr;
|
||||
dev_info(&pdev->dev, "fpga ocores nr is (%d), irq %d \n", i2c->adap.nr, irq);
|
||||
}
|
||||
i2c_set_adapdata(&i2c->adap, i2c);
|
||||
i2c->adap.dev.parent = &pdev->dev;
|
||||
i2c->adap.dev.of_node = pdev->dev.of_node;
|
||||
|
||||
/* add i2c adapter to i2c tree */
|
||||
ret = i2c_add_numbered_adapter(&i2c->adap);
|
||||
if (ret) {
|
||||
dev_err(&pdev->dev, "Failed to add adapter\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* add in known devices to the bus */
|
||||
if (pdata) {
|
||||
for (i = 0; i < pdata->num_devices; i++)
|
||||
i2c_new_device(&i2c->adap, pdata->devices + i);
|
||||
}
|
||||
|
||||
oc_debug_sysfs_init(pdev);
|
||||
oc_scl_clk_sysfs_init(&i2c->adap);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rg_ocores_i2c_remove(struct platform_device *pdev)
|
||||
{
|
||||
struct ocores_i2c *i2c = platform_get_drvdata(pdev);
|
||||
|
||||
/* disable i2c logic */
|
||||
oc_setreg(i2c, OCI2C_CONTROL, oc_getreg(i2c, OCI2C_CONTROL)
|
||||
& ~(OCI2C_CTRL_EN|OCI2C_CTRL_IEN));
|
||||
|
||||
/* remove adapter & data */
|
||||
oc_scl_clk_sysfs_exit(&i2c->adap);
|
||||
i2c_del_adapter(&i2c->adap);
|
||||
oc_debug_sysfs_exit(pdev);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_PM_SLEEP
|
||||
static int ocores_i2c_suspend(struct device *dev)
|
||||
{
|
||||
struct ocores_i2c *i2c = dev_get_drvdata(dev);
|
||||
u8 ctrl = oc_getreg(i2c, OCI2C_CONTROL);
|
||||
|
||||
/* make sure the device is disabled */
|
||||
oc_setreg(i2c, OCI2C_CONTROL, ctrl & ~(OCI2C_CTRL_EN|OCI2C_CTRL_IEN));
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int ocores_i2c_resume(struct device *dev)
|
||||
{
|
||||
struct ocores_i2c *i2c = dev_get_drvdata(dev);
|
||||
|
||||
ocores_init(i2c);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static SIMPLE_DEV_PM_OPS(ocores_i2c_pm, ocores_i2c_suspend, ocores_i2c_resume);
|
||||
#define OCORES_I2C_PM (&ocores_i2c_pm)
|
||||
#else
|
||||
#define OCORES_I2C_PM NULL
|
||||
#endif
|
||||
|
||||
static struct platform_driver ocores_i2c_driver = {
|
||||
.probe = rg_ocores_i2c_probe,
|
||||
.remove = rg_ocores_i2c_remove,
|
||||
.driver = {
|
||||
.owner = THIS_MODULE,
|
||||
.name = "rg-i2c-ocores",
|
||||
.of_match_table = ocores_i2c_match,
|
||||
.pm = OCORES_I2C_PM,
|
||||
},
|
||||
};
|
||||
|
||||
module_platform_driver(ocores_i2c_driver);
|
||||
|
||||
MODULE_AUTHOR("Peter Korsgaard <jacmet@sunsite.dk>");
|
||||
MODULE_DESCRIPTION("OpenCores I2C bus driver");
|
||||
MODULE_LICENSE("GPL");
|
||||
MODULE_ALIAS("platform:ocores-i2c");
|
@ -0,0 +1,13 @@
|
||||
#ifndef _FPGA_I2C_OCORES_H
|
||||
#define _FPGA_I2C_OCORES_H
|
||||
|
||||
struct rg_ocores_i2c_platform_data {
|
||||
u32 reg_shift; /* register offset shift value */
|
||||
u32 reg_io_width; /* register io read/write width */
|
||||
u32 clock_khz; /* input clock in kHz */
|
||||
u8 num_devices; /* number of devices in the devices list */
|
||||
struct i2c_board_info const *devices; /* devices connected to the bus */
|
||||
int nr; /* i2c bus num */
|
||||
};
|
||||
|
||||
#endif /* _FPGA_I2C_OCORES_H */
|
1144
platform/broadcom/sonic-platform-modules-ragile/common/modules/fpga_pcie_i2c.c
Executable file
1144
platform/broadcom/sonic-platform-modules-ragile/common/modules/fpga_pcie_i2c.c
Executable file
File diff suppressed because it is too large
Load Diff
107
platform/broadcom/sonic-platform-modules-ragile/common/modules/fpga_pcie_i2c.h
Executable file
107
platform/broadcom/sonic-platform-modules-ragile/common/modules/fpga_pcie_i2c.h
Executable file
@ -0,0 +1,107 @@
|
||||
#ifndef _FPGA_PCIE_I2C_H_
|
||||
#define _FPGA_PCIE_I2C_H_
|
||||
|
||||
#ifdef __KERNEL__
|
||||
#include <linux/types.h>
|
||||
#else
|
||||
#include <stdint.h>
|
||||
#endif
|
||||
|
||||
#define ENUM_MAX_DEVS (255)
|
||||
|
||||
typedef enum {
|
||||
CHIP_NONE,
|
||||
CHIP_PC,
|
||||
} chiptype_t;
|
||||
|
||||
/* bitmap for ports, 256 ports for now. */
|
||||
typedef struct portbitmap_s {
|
||||
uint8_t bit[32];
|
||||
} portbitmap_t;
|
||||
|
||||
typedef struct pc_info_s {
|
||||
uint8_t ntables; /* number of flow tables */
|
||||
uint8_t ncores; /* number of cores */
|
||||
uint8_t npipelines; /* number of pipelines */
|
||||
uint8_t nports; /* number of ports */
|
||||
portbitmap_t pbm_caui; /* bitmap for CAUI ports */
|
||||
portbitmap_t pbm_ge; /* bitmap for GE ports */
|
||||
} pc_info_t;
|
||||
|
||||
/**
|
||||
* A structure describing a PCI resource.
|
||||
*/
|
||||
struct pci_resource {
|
||||
uint64_t phys_addr; /**< Physical address, 0 if no resource. */
|
||||
uint64_t len; /**< Length of the resource. */
|
||||
void *addr; /**< Virtual address, NULL when not mapped. */
|
||||
};
|
||||
|
||||
/** Maximum number of PCI resources. */
|
||||
#define PCI_MAX_RESOURCE 6
|
||||
|
||||
/** Nb. of values in PCI resource format. */
|
||||
#define PCI_RESOURCE_FMT_NVAL 3
|
||||
|
||||
#if 0
|
||||
/** IO resource type: memory address space */
|
||||
#define IORESOURCE_MEM 0x00000200
|
||||
#endif
|
||||
|
||||
typedef struct chipinfo_s {
|
||||
/* PCI ID */
|
||||
uint16_t vendor;
|
||||
uint16_t dev;
|
||||
uint8_t rev;
|
||||
|
||||
/* chip properties */
|
||||
chiptype_t type;
|
||||
pc_info_t pc_info; /* if type == CHIP_PC */
|
||||
} chipinfo_t;
|
||||
|
||||
typedef struct devinfo_s {
|
||||
/* static info */
|
||||
chipinfo_t chipinfo;
|
||||
|
||||
/* running states */
|
||||
uint32_t uiono; /* the "X" in /dev/uioX */
|
||||
char *pci_conf_file; /* /sys/devices/ */
|
||||
char *dev_file; /* /dev/uioX */
|
||||
|
||||
struct pci_resource mem_resource[PCI_MAX_RESOURCE]; /**< PCI Memory Resource */
|
||||
|
||||
uint32_t n_mems; /* no of mem-mapped regions, MUST BE 1 for now */
|
||||
uint32_t n_ports;/* no of port-maped regions, MUST BE 0 for now */
|
||||
} devinfo_t;
|
||||
|
||||
|
||||
#ifdef __KERNEL__
|
||||
#include <linux/pci.h>
|
||||
|
||||
struct pci_dev *rgde_to_pci_device(int index);
|
||||
|
||||
int rgde_reg32_read(int minor, uint64_t offset, uint32_t *data);
|
||||
|
||||
int rgde_reg32_write(int minor, uint64_t offset, uint32_t data);
|
||||
|
||||
int pkt_get_mod(int logic_dev, int *mod);
|
||||
|
||||
int pkt_get_port(int logic_dev, int *port);
|
||||
|
||||
/* interrupt mode */
|
||||
enum xdk_intr_mode {
|
||||
XDK_INTR_MODE_NONE = 0,
|
||||
XDK_INTR_MODE_LEGACY,
|
||||
XDK_INTR_MODE_MSI,
|
||||
XDK_INTR_MODE_MSIX
|
||||
};
|
||||
|
||||
#define INTR_MODE_NONE_NAME "none"
|
||||
#define INTR_MODE_LEGACY_NAME "legacy"
|
||||
#define INTR_MODE_MSI_NAME "msi"
|
||||
#define INTR_MODE_MSIX_NAME "msix"
|
||||
|
||||
#endif /*__KERNEL__ */
|
||||
|
||||
|
||||
#endif /* _FPGA_PCIE_I2C_H_ */
|
174
platform/broadcom/sonic-platform-modules-ragile/common/modules/fpga_reg_defs.h
Executable file
174
platform/broadcom/sonic-platform-modules-ragile/common/modules/fpga_reg_defs.h
Executable file
@ -0,0 +1,174 @@
|
||||
#ifndef _FPGA_REG_DEFS_H_
|
||||
#define _FPGA_REG_DEFS_H_
|
||||
|
||||
/** Define Registers */
|
||||
/* Global Registers */
|
||||
#define RGDE_REG_GLOBAL_BASE 0x00000000
|
||||
#define RGDE_REG_VERSION (RGDE_REG_GLOBAL_BASE + 0x00)
|
||||
#define RGDE_REG_DATE (RGDE_REG_GLOBAL_BASE + 0x04)
|
||||
#define RGDE_REG_TEST (RGDE_REG_GLOBAL_BASE + 0x08)
|
||||
#define RGDE_REG_INT_ENABLE (RGDE_REG_GLOBAL_BASE + 0x10)
|
||||
#define RGDE_REG_INT_STATUS (RGDE_REG_GLOBAL_BASE + 0x14)
|
||||
|
||||
/* MDIO Registers */
|
||||
#define RGDE_REG_MDIO_BASE 0x00000100
|
||||
#define RGDE_REG_MDIO_CFG_DT (RGDE_REG_MDIO_BASE + 0x00)
|
||||
#define RGDE_REG_MDIO_CFG_SPEED (RGDE_REG_MDIO_BASE + 0x04)
|
||||
#define RGDE_REG_MDIO_CFG_START (RGDE_REG_MDIO_BASE + 0x08)
|
||||
#define RGDE_REG_MDIO_RDAT (RGDE_REG_MDIO_BASE + 0x10)
|
||||
#define RGDE_REG_MDIO_STATUS (RGDE_REG_MDIO_BASE + 0x14)
|
||||
|
||||
/* GE0 PORT Registers */
|
||||
#define RGDE_REG_GE0_PORT_BASE 0x00001000
|
||||
#define RGDE_REG_GE0_PORT_CTL (RGDE_REG_GE0_PORT_BASE + 0x00)
|
||||
#define RGDE_REG_GE0_PORT_STA (RGDE_REG_GE0_PORT_BASE + 0x04)
|
||||
#define RGDE_REG_GE0_PORT_MTU (RGDE_REG_GE0_PORT_BASE + 0x08)
|
||||
#define RGDE_REG_GE0_PORT_RXPKTS (RGDE_REG_GE0_PORT_BASE + 0x10)
|
||||
#define RGDE_REG_GE0_PORT_RXBYTE (RGDE_REG_GE0_PORT_BASE + 0x18)
|
||||
#define RGDE_REG_GE0_PORT_RXERR (RGDE_REG_GE0_PORT_BASE + 0x20)
|
||||
#define RGDE_REG_GE0_PORT_RXDROP (RGDE_REG_GE0_PORT_BASE + 0x28)
|
||||
#define RGDE_REG_GE0_PORT_RXMULTI (RGDE_REG_GE0_PORT_BASE + 0x30)
|
||||
#define RGDE_REG_GE0_PORT_RXBRO (RGDE_REG_GE0_PORT_BASE + 0x38)
|
||||
#define RGDE_REG_GE0_PORT_TXPKTS (RGDE_REG_GE0_PORT_BASE + 0x40)
|
||||
#define RGDE_REG_GE0_PORT_TXBYTE (RGDE_REG_GE0_PORT_BASE + 0x48)
|
||||
#define RGDE_REG_GE0_PORT_TXERR (RGDE_REG_GE0_PORT_BASE + 0x50)
|
||||
#define RGDE_REG_GE0_PORT_TXDROP (RGDE_REG_GE0_PORT_BASE + 0x58)
|
||||
#define RGDE_REG_GE0_PORT_TXMULT (RGDE_REG_GE0_PORT_BASE + 0x60)
|
||||
#define RGDE_REG_GE0_PORT_TXBRO (RGDE_REG_GE0_PORT_BASE + 0x68)
|
||||
|
||||
/* GE1 PORT Registers */
|
||||
#define RGDE_REG_GE1_PORT_BASE 0x00001100
|
||||
#define RGDE_REG_GE1_PORT_CTL (RGDE_REG_GE1_PORT_BASE + 0x00)
|
||||
#define RGDE_REG_GE1_PORT_STA (RGDE_REG_GE1_PORT_BASE + 0x04)
|
||||
#define RGDE_REG_GE1_PORT_MTU (RGDE_REG_GE1_PORT_BASE + 0x08)
|
||||
#define RGDE_REG_GE1_PORT_RXPKTS (RGDE_REG_GE1_PORT_BASE + 0x10)
|
||||
#define RGDE_REG_GE1_PORT_RXBYTE (RGDE_REG_GE1_PORT_BASE + 0x18)
|
||||
#define RGDE_REG_GE1_PORT_RXERR (RGDE_REG_GE1_PORT_BASE + 0x20)
|
||||
#define RGDE_REG_GE1_PORT_RXDROP (RGDE_REG_GE1_PORT_BASE + 0x28)
|
||||
#define RGDE_REG_GE1_PORT_RXMULTI (RGDE_REG_GE1_PORT_BASE + 0x30)
|
||||
#define RGDE_REG_GE1_PORT_RXBRO (RGDE_REG_GE1_PORT_BASE + 0x38)
|
||||
#define RGDE_REG_GE1_PORT_TXPKTS (RGDE_REG_GE1_PORT_BASE + 0x40)
|
||||
#define RGDE_REG_GE1_PORT_TXBYTE (RGDE_REG_GE1_PORT_BASE + 0x48)
|
||||
#define RGDE_REG_GE1_PORT_TXERR (RGDE_REG_GE1_PORT_BASE + 0x50)
|
||||
#define RGDE_REG_GE1_PORT_TXDROP (RGDE_REG_GE1_PORT_BASE + 0x58)
|
||||
#define RGDE_REG_GE1_PORT_TXMULT (RGDE_REG_GE1_PORT_BASE + 0x60)
|
||||
#define RGDE_REG_GE1_PORT_TXBRO (RGDE_REG_GE1_PORT_BASE + 0x68)
|
||||
|
||||
/* GE2 PORT Registers */
|
||||
#define RGDE_REG_GE2_PORT_BASE 0x00001200
|
||||
#define RGDE_REG_GE2_PORT_CTL (RGDE_REG_GE2_PORT_BASE + 0x00)
|
||||
#define RGDE_REG_GE2_PORT_STA (RGDE_REG_GE2_PORT_BASE + 0x04)
|
||||
#define RGDE_REG_GE2_PORT_MTU (RGDE_REG_GE2_PORT_BASE + 0x08)
|
||||
#define RGDE_REG_GE2_PORT_RXPKTS (RGDE_REG_GE2_PORT_BASE + 0x10)
|
||||
#define RGDE_REG_GE2_PORT_RXBYTE (RGDE_REG_GE2_PORT_BASE + 0x18)
|
||||
#define RGDE_REG_GE2_PORT_RXERR (RGDE_REG_GE2_PORT_BASE + 0x20)
|
||||
#define RGDE_REG_GE2_PORT_RXDROP (RGDE_REG_GE2_PORT_BASE + 0x28)
|
||||
#define RGDE_REG_GE2_PORT_RXMULTI (RGDE_REG_GE2_PORT_BASE + 0x30)
|
||||
#define RGDE_REG_GE2_PORT_RXBRO (RGDE_REG_GE2_PORT_BASE + 0x38)
|
||||
#define RGDE_REG_GE2_PORT_TXPKTS (RGDE_REG_GE2_PORT_BASE + 0x40)
|
||||
#define RGDE_REG_GE2_PORT_TXBYTE (RGDE_REG_GE2_PORT_BASE + 0x48)
|
||||
#define RGDE_REG_GE2_PORT_TXERR (RGDE_REG_GE2_PORT_BASE + 0x50)
|
||||
#define RGDE_REG_GE2_PORT_TXDROP (RGDE_REG_GE2_PORT_BASE + 0x58)
|
||||
#define RGDE_REG_GE2_PORT_TXMULT (RGDE_REG_GE2_PORT_BASE + 0x60)
|
||||
#define RGDE_REG_GE2_PORT_TXBRO (RGDE_REG_GE2_PORT_BASE + 0x68)
|
||||
|
||||
/* GE3 PORT Registers */
|
||||
#define RGDE_REG_GE3_PORT_BASE 0x00001300
|
||||
#define RGDE_REG_GE3_PORT_CTL (RGDE_REG_GE3_PORT_BASE + 0x00)
|
||||
#define RGDE_REG_GE3_PORT_STA (RGDE_REG_GE3_PORT_BASE + 0x04)
|
||||
#define RGDE_REG_GE3_PORT_MTU (RGDE_REG_GE3_PORT_BASE + 0x08)
|
||||
#define RGDE_REG_GE3_PORT_RXPKTS (RGDE_REG_GE3_PORT_BASE + 0x10)
|
||||
#define RGDE_REG_GE3_PORT_RXBYTE (RGDE_REG_GE3_PORT_BASE + 0x18)
|
||||
#define RGDE_REG_GE3_PORT_RXERR (RGDE_REG_GE3_PORT_BASE + 0x20)
|
||||
#define RGDE_REG_GE3_PORT_RXDROP (RGDE_REG_GE3_PORT_BASE + 0x28)
|
||||
#define RGDE_REG_GE3_PORT_RXMULTI (RGDE_REG_GE3_PORT_BASE + 0x30)
|
||||
#define RGDE_REG_GE3_PORT_RXBRO (RGDE_REG_GE3_PORT_BASE + 0x38)
|
||||
#define RGDE_REG_GE3_PORT_TXPKTS (RGDE_REG_GE3_PORT_BASE + 0x40)
|
||||
#define RGDE_REG_GE3_PORT_TXBYTE (RGDE_REG_GE3_PORT_BASE + 0x48)
|
||||
#define RGDE_REG_GE3_PORT_TXERR (RGDE_REG_GE3_PORT_BASE + 0x50)
|
||||
#define RGDE_REG_GE3_PORT_TXDROP (RGDE_REG_GE3_PORT_BASE + 0x58)
|
||||
#define RGDE_REG_GE3_PORT_TXMULT (RGDE_REG_GE3_PORT_BASE + 0x60)
|
||||
#define RGDE_REG_GE3_PORT_TXBRO (RGDE_REG_GE3_PORT_BASE + 0x68)
|
||||
|
||||
/* GE4 PORT Registers */
|
||||
#define RGDE_REG_XGE0_PORT_BASE 0x00001400
|
||||
#define RGDE_REG_XGE0_PORT_CTL (RGDE_REG_XGE0_PORT_BASE + 0x00)
|
||||
#define RGDE_REG_XGE0_PORT_STA (RGDE_REG_XGE0_PORT_BASE + 0x04)
|
||||
#define RGDE_REG_XGE0_PORT_MTU (RGDE_REG_XGE0_PORT_BASE + 0x08)
|
||||
#define RGDE_REG_XGE0_PORT_RXPKTS (RGDE_REG_XGE0_PORT_BASE + 0x10)
|
||||
#define RGDE_REG_XGE0_PORT_RXBYTE (RGDE_REG_XGE0_PORT_BASE + 0x18)
|
||||
#define RGDE_REG_XGE0_PORT_RXERR (RGDE_REG_XGE0_PORT_BASE + 0x20)
|
||||
#define RGDE_REG_XGE0_PORT_RXDROP (RGDE_REG_XGE0_PORT_BASE + 0x28)
|
||||
#define RGDE_REG_XGE0_PORT_RXMULTI (RGDE_REG_XGE0_PORT_BASE + 0x30)
|
||||
#define RGDE_REG_XGE0_PORT_RXBRO (RGDE_REG_XGE0_PORT_BASE + 0x38)
|
||||
#define RGDE_REG_XGE0_PORT_TXPKTS (RGDE_REG_XGE0_PORT_BASE + 0x40)
|
||||
#define RGDE_REG_XGE0_PORT_TXBYTE (RGDE_REG_XGE0_PORT_BASE + 0x48)
|
||||
#define RGDE_REG_XGE0_PORT_TXERR (RGDE_REG_XGE0_PORT_BASE + 0x50)
|
||||
#define RGDE_REG_XGE0_PORT_TXDROP (RGDE_REG_XGE0_PORT_BASE + 0x58)
|
||||
#define RGDE_REG_XGE0_PORT_TXMULT (RGDE_REG_XGE0_PORT_BASE + 0x60)
|
||||
#define RGDE_REG_XGE0_PORT_TXBRO (RGDE_REG_XGE0_PORT_BASE + 0x68)
|
||||
|
||||
/* GE5 PORT Registers */
|
||||
#define RGDE_REG_XGE1_PORT_BASE 0x00001500
|
||||
#define RGDE_REG_XGE1_PORT_CTL (RGDE_REG_XGE1_PORT_BASE + 0x00)
|
||||
#define RGDE_REG_XGE1_PORT_STA (RGDE_REG_XGE1_PORT_BASE + 0x04)
|
||||
#define RGDE_REG_XGE1_PORT_MTU (RGDE_REG_XGE1_PORT_BASE + 0x08)
|
||||
#define RGDE_REG_XGE1_PORT_RXPKTS (RGDE_REG_XGE1_PORT_BASE + 0x10)
|
||||
#define RGDE_REG_XGE1_PORT_RXBYTE (RGDE_REG_XGE1_PORT_BASE + 0x18)
|
||||
#define RGDE_REG_XGE1_PORT_RXERR (RGDE_REG_XGE1_PORT_BASE + 0x20)
|
||||
#define RGDE_REG_XGE1_PORT_RXDROP (RGDE_REG_XGE1_PORT_BASE + 0x28)
|
||||
#define RGDE_REG_XGE1_PORT_RXMULTI (RGDE_REG_XGE1_PORT_BASE + 0x30)
|
||||
#define RGDE_REG_XGE1_PORT_RXBRO (RGDE_REG_XGE1_PORT_BASE + 0x38)
|
||||
#define RGDE_REG_XGE1_PORT_TXPKTS (RGDE_REG_XGE1_PORT_BASE + 0x40)
|
||||
#define RGDE_REG_XGE1_PORT_TXBYTE (RGDE_REG_XGE1_PORT_BASE + 0x48)
|
||||
#define RGDE_REG_XGE1_PORT_TXERR (RGDE_REG_XGE1_PORT_BASE + 0x50)
|
||||
#define RGDE_REG_XGE1_PORT_TXDROP (RGDE_REG_XGE1_PORT_BASE + 0x58)
|
||||
#define RGDE_REG_XGE1_PORT_TXMULT (RGDE_REG_XGE1_PORT_BASE + 0x60)
|
||||
#define RGDE_REG_XGE1_PORT_TXBRO (RGDE_REG_XGE1_PORT_BASE + 0x68)
|
||||
|
||||
#define RGDE_REG_CPU_BASE 0x00002100
|
||||
#define RGDE_REG_PCIE_ENDIAN_CNTR (RGDE_REG_CPU_BASE + 0x08)
|
||||
|
||||
/* DMA Registers */
|
||||
#define RGDE_REG_DMA_BASE 0x00004000
|
||||
#define RGDE_REG_BD_WR_OVERTIME (RGDE_REG_DMA_BASE + 0x00)
|
||||
#define RGDE_REG_BD_DEEP (RGDE_REG_DMA_BASE + 0x04)
|
||||
|
||||
/* TX0 Registers */
|
||||
#define RGDE_REG_TX0_BASE 0x00005000
|
||||
#define RGDE_REG_TX0_CHN_EN (RGDE_REG_TX0_BASE + 0x00)
|
||||
#define RGDE_REG_TX0_BD_BASE (RGDE_REG_TX0_BASE + 0x04)
|
||||
#define RGDE_REG_TX0_BD_TAIL (RGDE_REG_TX0_BASE + 0x08)
|
||||
#define RGDE_REG_TX0_BD_READY_NUM (RGDE_REG_TX0_BASE + 0x0c)
|
||||
#define RGDE_REG_TX0_CPU2FPGA_BD_NUM (RGDE_REG_TX0_BASE + 0x30)
|
||||
#define RGDE_REG_TX0_FPGA2CPU_BD_NUM (RGDE_REG_TX0_BASE + 0x34)
|
||||
|
||||
/* TX1 Registers */
|
||||
#define RGDE_REG_TX1_BASE 0x00005100
|
||||
#define RGDE_REG_TX1_CHN_EN (RGDE_REG_TX1_BASE + 0x00)
|
||||
#define RGDE_REG_TX1_BD_BASE (RGDE_REG_TX1_BASE + 0x04)
|
||||
#define RGDE_REG_TX1_BD_TAIL (RGDE_REG_TX1_BASE + 0x08)
|
||||
#define RGDE_REG_TX1_BD_READY_NUM (RGDE_REG_TX1_BASE + 0x0c)
|
||||
#define RGDE_REG_TX1_CPU2FPGA_BD_NUM (RGDE_REG_TX1_BASE + 0x30)
|
||||
#define RGDE_REG_TX1_FPGA2CPU_BD_NUM (RGDE_REG_TX1_BASE + 0x34)
|
||||
|
||||
/* RX0 Registers */
|
||||
#define RGDE_REG_RX0_BASE 0x00006400
|
||||
#define RGDE_REG_RX0_CHN_EN (RGDE_REG_RX0_BASE + 0x00)
|
||||
#define RGDE_REG_RX0_BD_BASE (RGDE_REG_RX0_BASE + 0x04)
|
||||
#define RGDE_REG_RX0_BD_TAIL (RGDE_REG_RX0_BASE + 0x08)
|
||||
#define RGDE_REG_RX0_BD_READY_NUM (RGDE_REG_RX0_BASE + 0x0c)
|
||||
#define RGDE_REG_RX0_CPU2FPGA_BD_NUM (RGDE_REG_RX0_BASE + 0x30)
|
||||
#define RGDE_REG_RX0_FPGA2CPU_BD_NUM (RGDE_REG_RX0_BASE + 0x34)
|
||||
|
||||
/* RX1 Registers */
|
||||
#define RGDE_REG_RX1_BASE 0x00006500
|
||||
#define RGDE_REG_RX1_CHN_EN (RGDE_REG_RX1_BASE + 0x00)
|
||||
#define RGDE_REG_RX1_BD_BASE (RGDE_REG_RX1_BASE + 0x04)
|
||||
#define RGDE_REG_RX1_BD_TAIL (RGDE_REG_RX1_BASE + 0x08)
|
||||
#define RGDE_REG_RX1_BD_READY_NUM (RGDE_REG_RX1_BASE + 0x0c)
|
||||
#define RGDE_REG_RX1_CPU2FPGA_BD_NUM (RGDE_REG_RX1_BASE + 0x30)
|
||||
#define RGDE_REG_RX1_FPGA2CPU_BD_NUM (RGDE_REG_RX1_BASE + 0x34)
|
||||
|
||||
|
||||
#endif /* _FPGA_REG_DEFS_H_ */
|
File diff suppressed because it is too large
Load Diff
@ -40,22 +40,22 @@
|
||||
* that only one of the masters is instantiated at any given time.
|
||||
*/
|
||||
|
||||
#define PCA9541_CONTROL 0x01
|
||||
#define PCA9541_ISTAT 0x02
|
||||
#define PCA9541_CONTROL 0x01
|
||||
#define PCA9541_ISTAT 0x02
|
||||
|
||||
#define PCA9541_CTL_MYBUS (1 << 0)
|
||||
#define PCA9541_CTL_NMYBUS (1 << 1)
|
||||
#define PCA9541_CTL_BUSON (1 << 2)
|
||||
#define PCA9541_CTL_NBUSON (1 << 3)
|
||||
#define PCA9541_CTL_BUSINIT (1 << 4)
|
||||
#define PCA9541_CTL_TESTON (1 << 6)
|
||||
#define PCA9541_CTL_NTESTON (1 << 7)
|
||||
#define PCA9541_ISTAT_INTIN (1 << 0)
|
||||
#define PCA9541_ISTAT_BUSINIT (1 << 1)
|
||||
#define PCA9541_ISTAT_BUSOK (1 << 2)
|
||||
#define PCA9541_ISTAT_BUSLOST (1 << 3)
|
||||
#define PCA9541_ISTAT_MYTEST (1 << 6)
|
||||
#define PCA9541_ISTAT_NMYTEST (1 << 7)
|
||||
#define PCA9541_CTL_MYBUS (1 << 0)
|
||||
#define PCA9541_CTL_NMYBUS (1 << 1)
|
||||
#define PCA9541_CTL_BUSON (1 << 2)
|
||||
#define PCA9541_CTL_NBUSON (1 << 3)
|
||||
#define PCA9541_CTL_BUSINIT (1 << 4)
|
||||
#define PCA9541_CTL_TESTON (1 << 6)
|
||||
#define PCA9541_CTL_NTESTON (1 << 7)
|
||||
#define PCA9541_ISTAT_INTIN (1 << 0)
|
||||
#define PCA9541_ISTAT_BUSINIT (1 << 1)
|
||||
#define PCA9541_ISTAT_BUSOK (1 << 2)
|
||||
#define PCA9541_ISTAT_BUSLOST (1 << 3)
|
||||
#define PCA9541_ISTAT_MYTEST (1 << 6)
|
||||
#define PCA9541_ISTAT_NMYTEST (1 << 7)
|
||||
#define PCA9641_ID 0x00
|
||||
#define PCA9641_ID_MAGIC 0x38
|
||||
#define PCA9641_CONTROL 0x01
|
||||
@ -78,12 +78,12 @@
|
||||
#define PCA9641_STS_SCL_IO BIT(6)
|
||||
#define PCA9641_STS_SDA_IO BIT(7)
|
||||
#define PCA9641_RES_TIME 0x03
|
||||
#define BUSON (PCA9541_CTL_BUSON | PCA9541_CTL_NBUSON)
|
||||
#define MYBUS (PCA9541_CTL_MYBUS | PCA9541_CTL_NMYBUS)
|
||||
#define mybus(x) (!((x) & MYBUS) || ((x) & MYBUS) == MYBUS)
|
||||
#define busoff(x) (!((x) & BUSON) || ((x) & BUSON) == BUSON)
|
||||
#define BUSON (PCA9541_CTL_BUSON | PCA9541_CTL_NBUSON)
|
||||
#define MYBUS (PCA9541_CTL_MYBUS | PCA9541_CTL_NMYBUS)
|
||||
#define mybus(x) (!((x) & MYBUS) || ((x) & MYBUS) == MYBUS)
|
||||
#define busoff(x) (!((x) & BUSON) || ((x) & BUSON) == BUSON)
|
||||
#define BUSOFF(x, y) (!((x) & PCA9641_CTL_LOCK_GRANT) && \
|
||||
!((y) & PCA9641_STS_OTHER_LOCK))
|
||||
!((y) & PCA9641_STS_OTHER_LOCK))
|
||||
#define other_lock(x) ((x) & PCA9641_STS_OTHER_LOCK)
|
||||
#define lock_grant(x) ((x) & PCA9641_CTL_LOCK_GRANT)
|
||||
|
||||
@ -91,22 +91,22 @@
|
||||
|
||||
typedef struct i2c_muxs_struct_flag
|
||||
{
|
||||
int nr;
|
||||
char name[48];
|
||||
struct mutex update_lock;
|
||||
int flag;
|
||||
int nr;
|
||||
char name[48];
|
||||
struct mutex update_lock;
|
||||
int flag;
|
||||
}i2c_mux_flag;
|
||||
|
||||
i2c_mux_flag pca_flag = {
|
||||
.flag = -1,
|
||||
.flag = -1,
|
||||
};
|
||||
|
||||
int pca9641_setmuxflag(int nr, int flag)
|
||||
{
|
||||
if (pca_flag.nr == nr) {
|
||||
pca_flag.flag = flag;
|
||||
}
|
||||
return 0;
|
||||
if (pca_flag.nr == nr) {
|
||||
pca_flag.flag = flag;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
EXPORT_SYMBOL(pca9641_setmuxflag);
|
||||
|
||||
@ -121,23 +121,23 @@ module_param(g_debug, int, S_IRUGO | S_IWUSR);
|
||||
|
||||
|
||||
/* arbitration timeouts, in jiffies */
|
||||
#define ARB_TIMEOUT (HZ / 8) /* 125 ms until forcing bus ownership */
|
||||
#define ARB2_TIMEOUT (HZ / 4) /* 250 ms until acquisition failure */
|
||||
#define ARB_TIMEOUT (HZ / 8) /* 125 ms until forcing bus ownership */
|
||||
#define ARB2_TIMEOUT (HZ / 4) /* 250 ms until acquisition failure */
|
||||
|
||||
/* arbitration retry delays, in us */
|
||||
#define SELECT_DELAY_SHORT 50
|
||||
#define SELECT_DELAY_LONG 1000
|
||||
#define SELECT_DELAY_SHORT 50
|
||||
#define SELECT_DELAY_LONG 1000
|
||||
|
||||
struct pca9541 {
|
||||
struct i2c_client *client;
|
||||
unsigned long select_timeout;
|
||||
unsigned long arb_timeout;
|
||||
struct i2c_client *client;
|
||||
unsigned long select_timeout;
|
||||
unsigned long arb_timeout;
|
||||
};
|
||||
|
||||
static const struct i2c_device_id pca9541_id[] = {
|
||||
{"pca9541", 0},
|
||||
{"pca9641", 1},
|
||||
{}
|
||||
{"pca9541", 0},
|
||||
{"pca9641", 1},
|
||||
{}
|
||||
};
|
||||
|
||||
MODULE_DEVICE_TABLE(i2c, pca9541_id);
|
||||
@ -158,32 +158,32 @@ MODULE_DEVICE_TABLE(of, pca9541_of_match);
|
||||
*/
|
||||
static int pca9541_reg_write(struct i2c_client *client, u8 command, u8 val)
|
||||
{
|
||||
struct i2c_adapter *adap = client->adapter;
|
||||
int ret;
|
||||
struct i2c_adapter *adap = client->adapter;
|
||||
int ret;
|
||||
|
||||
if (adap->algo->master_xfer) {
|
||||
struct i2c_msg msg;
|
||||
char buf[2];
|
||||
if (adap->algo->master_xfer) {
|
||||
struct i2c_msg msg;
|
||||
char buf[2];
|
||||
|
||||
msg.addr = client->addr;
|
||||
msg.flags = 0;
|
||||
msg.len = 2;
|
||||
buf[0] = command;
|
||||
buf[1] = val;
|
||||
msg.buf = buf;
|
||||
ret = __i2c_transfer(adap, &msg, 1);
|
||||
} else {
|
||||
union i2c_smbus_data data;
|
||||
msg.addr = client->addr;
|
||||
msg.flags = 0;
|
||||
msg.len = 2;
|
||||
buf[0] = command;
|
||||
buf[1] = val;
|
||||
msg.buf = buf;
|
||||
ret = __i2c_transfer(adap, &msg, 1);
|
||||
} else {
|
||||
union i2c_smbus_data data;
|
||||
|
||||
data.byte = val;
|
||||
ret = adap->algo->smbus_xfer(adap, client->addr,
|
||||
client->flags,
|
||||
I2C_SMBUS_WRITE,
|
||||
command,
|
||||
I2C_SMBUS_BYTE_DATA, &data);
|
||||
}
|
||||
data.byte = val;
|
||||
ret = adap->algo->smbus_xfer(adap, client->addr,
|
||||
client->flags,
|
||||
I2C_SMBUS_WRITE,
|
||||
command,
|
||||
I2C_SMBUS_BYTE_DATA, &data);
|
||||
}
|
||||
|
||||
return ret;
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -192,42 +192,42 @@ static int pca9541_reg_write(struct i2c_client *client, u8 command, u8 val)
|
||||
*/
|
||||
static int pca9541_reg_read(struct i2c_client *client, u8 command)
|
||||
{
|
||||
struct i2c_adapter *adap = client->adapter;
|
||||
int ret;
|
||||
u8 val;
|
||||
struct i2c_adapter *adap = client->adapter;
|
||||
int ret;
|
||||
u8 val;
|
||||
|
||||
if (adap->algo->master_xfer) {
|
||||
struct i2c_msg msg[2] = {
|
||||
{
|
||||
.addr = client->addr,
|
||||
.flags = 0,
|
||||
.len = 1,
|
||||
.buf = &command
|
||||
},
|
||||
{
|
||||
.addr = client->addr,
|
||||
.flags = I2C_M_RD,
|
||||
.len = 1,
|
||||
.buf = &val
|
||||
}
|
||||
};
|
||||
ret = __i2c_transfer(adap, msg, 2);
|
||||
if (ret == 2)
|
||||
ret = val;
|
||||
else if (ret >= 0)
|
||||
ret = -EIO;
|
||||
} else {
|
||||
union i2c_smbus_data data;
|
||||
if (adap->algo->master_xfer) {
|
||||
struct i2c_msg msg[2] = {
|
||||
{
|
||||
.addr = client->addr,
|
||||
.flags = 0,
|
||||
.len = 1,
|
||||
.buf = &command
|
||||
},
|
||||
{
|
||||
.addr = client->addr,
|
||||
.flags = I2C_M_RD,
|
||||
.len = 1,
|
||||
.buf = &val
|
||||
}
|
||||
};
|
||||
ret = __i2c_transfer(adap, msg, 2);
|
||||
if (ret == 2)
|
||||
ret = val;
|
||||
else if (ret >= 0)
|
||||
ret = -EIO;
|
||||
} else {
|
||||
union i2c_smbus_data data;
|
||||
|
||||
ret = adap->algo->smbus_xfer(adap, client->addr,
|
||||
client->flags,
|
||||
I2C_SMBUS_READ,
|
||||
command,
|
||||
I2C_SMBUS_BYTE_DATA, &data);
|
||||
if (!ret)
|
||||
ret = data.byte;
|
||||
}
|
||||
return ret;
|
||||
ret = adap->algo->smbus_xfer(adap, client->addr,
|
||||
client->flags,
|
||||
I2C_SMBUS_READ,
|
||||
command,
|
||||
I2C_SMBUS_BYTE_DATA, &data);
|
||||
if (!ret)
|
||||
ret = data.byte;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -237,12 +237,12 @@ static int pca9541_reg_read(struct i2c_client *client, u8 command)
|
||||
/* Release bus. Also reset NTESTON and BUSINIT if it was set. */
|
||||
static void pca9541_release_bus(struct i2c_client *client)
|
||||
{
|
||||
int reg;
|
||||
int reg;
|
||||
|
||||
reg = pca9541_reg_read(client, PCA9541_CONTROL);
|
||||
if (reg >= 0 && !busoff(reg) && mybus(reg))
|
||||
pca9541_reg_write(client, PCA9541_CONTROL,
|
||||
(reg & PCA9541_CTL_NBUSON) >> 1);
|
||||
reg = pca9541_reg_read(client, PCA9541_CONTROL);
|
||||
if (reg >= 0 && !busoff(reg) && mybus(reg))
|
||||
pca9541_reg_write(client, PCA9541_CONTROL,
|
||||
(reg & PCA9541_CTL_NBUSON) >> 1);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -251,16 +251,16 @@ static void pca9541_release_bus(struct i2c_client *client)
|
||||
* This multi-step process ensures that access contention is resolved
|
||||
* gracefully.
|
||||
*
|
||||
* Bus Ownership Other master Action
|
||||
* state requested access
|
||||
* Bus Ownership Other master Action
|
||||
* state requested access
|
||||
* ----------------------------------------------------
|
||||
* off - yes wait for arbitration timeout or
|
||||
* for other master to drop request
|
||||
* off no no take ownership
|
||||
* off yes no turn on bus
|
||||
* on yes - done
|
||||
* on no - wait for arbitration timeout or
|
||||
* for other master to release bus
|
||||
* off - yes wait for arbitration timeout or
|
||||
* for other master to drop request
|
||||
* off no no take ownership
|
||||
* off yes no turn on bus
|
||||
* on yes - done
|
||||
* on no - wait for arbitration timeout or
|
||||
* for other master to release bus
|
||||
*
|
||||
* The main contention point occurs if the slave bus is off and both masters
|
||||
* request ownership at the same time. In this case, one master will turn on
|
||||
@ -271,7 +271,7 @@ static void pca9541_release_bus(struct i2c_client *client)
|
||||
|
||||
/* Control commands per PCA9541 datasheet */
|
||||
static const u8 pca9541_control[16] = {
|
||||
4, 0, 1, 5, 4, 4, 5, 5, 0, 0, 1, 1, 0, 4, 5, 1
|
||||
4, 0, 1, 5, 4, 4, 5, 5, 0, 0, 1, 1, 0, 4, 5, 1
|
||||
};
|
||||
|
||||
/*
|
||||
@ -284,187 +284,187 @@ static const u8 pca9541_control[16] = {
|
||||
*/
|
||||
static int pca9541_arbitrate(struct i2c_client *client)
|
||||
{
|
||||
struct i2c_mux_core *muxc = i2c_get_clientdata(client);
|
||||
struct pca9541 *data = i2c_mux_priv(muxc);
|
||||
int reg;
|
||||
struct i2c_mux_core *muxc = i2c_get_clientdata(client);
|
||||
struct pca9541 *data = i2c_mux_priv(muxc);
|
||||
int reg;
|
||||
|
||||
reg = pca9541_reg_read(client, PCA9541_CONTROL);
|
||||
if (reg < 0)
|
||||
return reg;
|
||||
reg = pca9541_reg_read(client, PCA9541_CONTROL);
|
||||
if (reg < 0)
|
||||
return reg;
|
||||
|
||||
if (busoff(reg)) {
|
||||
int istat;
|
||||
/*
|
||||
* Bus is off. Request ownership or turn it on unless
|
||||
* other master requested ownership.
|
||||
*/
|
||||
istat = pca9541_reg_read(client, PCA9541_ISTAT);
|
||||
if (!(istat & PCA9541_ISTAT_NMYTEST)
|
||||
|| time_is_before_eq_jiffies(data->arb_timeout)) {
|
||||
/*
|
||||
* Other master did not request ownership,
|
||||
* or arbitration timeout expired. Take the bus.
|
||||
*/
|
||||
pca9541_reg_write(client,
|
||||
PCA9541_CONTROL,
|
||||
pca9541_control[reg & 0x0f]
|
||||
| PCA9541_CTL_NTESTON);
|
||||
data->select_timeout = SELECT_DELAY_SHORT;
|
||||
} else {
|
||||
/*
|
||||
* Other master requested ownership.
|
||||
* Set extra long timeout to give it time to acquire it.
|
||||
*/
|
||||
data->select_timeout = SELECT_DELAY_LONG * 2;
|
||||
}
|
||||
} else if (mybus(reg)) {
|
||||
/*
|
||||
* Bus is on, and we own it. We are done with acquisition.
|
||||
* Reset NTESTON and BUSINIT, then return success.
|
||||
*/
|
||||
if (reg & (PCA9541_CTL_NTESTON | PCA9541_CTL_BUSINIT))
|
||||
pca9541_reg_write(client,
|
||||
PCA9541_CONTROL,
|
||||
reg & ~(PCA9541_CTL_NTESTON
|
||||
| PCA9541_CTL_BUSINIT));
|
||||
return 1;
|
||||
} else {
|
||||
/*
|
||||
* Other master owns the bus.
|
||||
* If arbitration timeout has expired, force ownership.
|
||||
* Otherwise request it.
|
||||
*/
|
||||
data->select_timeout = SELECT_DELAY_LONG;
|
||||
if (time_is_before_eq_jiffies(data->arb_timeout)) {
|
||||
/* Time is up, take the bus and reset it. */
|
||||
pca9541_reg_write(client,
|
||||
PCA9541_CONTROL,
|
||||
pca9541_control[reg & 0x0f]
|
||||
| PCA9541_CTL_BUSINIT
|
||||
| PCA9541_CTL_NTESTON);
|
||||
} else {
|
||||
/* Request bus ownership if needed */
|
||||
if (!(reg & PCA9541_CTL_NTESTON))
|
||||
pca9541_reg_write(client,
|
||||
PCA9541_CONTROL,
|
||||
reg | PCA9541_CTL_NTESTON);
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
if (busoff(reg)) {
|
||||
int istat;
|
||||
/*
|
||||
* Bus is off. Request ownership or turn it on unless
|
||||
* other master requested ownership.
|
||||
*/
|
||||
istat = pca9541_reg_read(client, PCA9541_ISTAT);
|
||||
if (!(istat & PCA9541_ISTAT_NMYTEST)
|
||||
|| time_is_before_eq_jiffies(data->arb_timeout)) {
|
||||
/*
|
||||
* Other master did not request ownership,
|
||||
* or arbitration timeout expired. Take the bus.
|
||||
*/
|
||||
pca9541_reg_write(client,
|
||||
PCA9541_CONTROL,
|
||||
pca9541_control[reg & 0x0f]
|
||||
| PCA9541_CTL_NTESTON);
|
||||
data->select_timeout = SELECT_DELAY_SHORT;
|
||||
} else {
|
||||
/*
|
||||
* Other master requested ownership.
|
||||
* Set extra long timeout to give it time to acquire it.
|
||||
*/
|
||||
data->select_timeout = SELECT_DELAY_LONG * 2;
|
||||
}
|
||||
} else if (mybus(reg)) {
|
||||
/*
|
||||
* Bus is on, and we own it. We are done with acquisition.
|
||||
* Reset NTESTON and BUSINIT, then return success.
|
||||
*/
|
||||
if (reg & (PCA9541_CTL_NTESTON | PCA9541_CTL_BUSINIT))
|
||||
pca9541_reg_write(client,
|
||||
PCA9541_CONTROL,
|
||||
reg & ~(PCA9541_CTL_NTESTON
|
||||
| PCA9541_CTL_BUSINIT));
|
||||
return 1;
|
||||
} else {
|
||||
/*
|
||||
* Other master owns the bus.
|
||||
* If arbitration timeout has expired, force ownership.
|
||||
* Otherwise request it.
|
||||
*/
|
||||
data->select_timeout = SELECT_DELAY_LONG;
|
||||
if (time_is_before_eq_jiffies(data->arb_timeout)) {
|
||||
/* Time is up, take the bus and reset it. */
|
||||
pca9541_reg_write(client,
|
||||
PCA9541_CONTROL,
|
||||
pca9541_control[reg & 0x0f]
|
||||
| PCA9541_CTL_BUSINIT
|
||||
| PCA9541_CTL_NTESTON);
|
||||
} else {
|
||||
/* Request bus ownership if needed */
|
||||
if (!(reg & PCA9541_CTL_NTESTON))
|
||||
pca9541_reg_write(client,
|
||||
PCA9541_CONTROL,
|
||||
reg | PCA9541_CTL_NTESTON);
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int pca9541_select_chan(struct i2c_mux_core *muxc, u32 chan)
|
||||
{
|
||||
struct pca9541 *data = i2c_mux_priv(muxc);
|
||||
struct i2c_client *client = data->client;
|
||||
int ret;
|
||||
unsigned long timeout = jiffies + ARB2_TIMEOUT;
|
||||
/* give up after this time */
|
||||
struct pca9541 *data = i2c_mux_priv(muxc);
|
||||
struct i2c_client *client = data->client;
|
||||
int ret;
|
||||
unsigned long timeout = jiffies + ARB2_TIMEOUT;
|
||||
/* give up after this time */
|
||||
|
||||
data->arb_timeout = jiffies + ARB_TIMEOUT;
|
||||
/* force bus ownership after this time */
|
||||
data->arb_timeout = jiffies + ARB_TIMEOUT;
|
||||
/* force bus ownership after this time */
|
||||
|
||||
do {
|
||||
ret = pca9541_arbitrate(client);
|
||||
if (ret)
|
||||
return ret < 0 ? ret : 0;
|
||||
do {
|
||||
ret = pca9541_arbitrate(client);
|
||||
if (ret)
|
||||
return ret < 0 ? ret : 0;
|
||||
|
||||
if (data->select_timeout == SELECT_DELAY_SHORT)
|
||||
udelay(data->select_timeout);
|
||||
else
|
||||
msleep(data->select_timeout / 1000);
|
||||
} while (time_is_after_eq_jiffies(timeout));
|
||||
if (data->select_timeout == SELECT_DELAY_SHORT)
|
||||
udelay(data->select_timeout);
|
||||
else
|
||||
msleep(data->select_timeout / 1000);
|
||||
} while (time_is_after_eq_jiffies(timeout));
|
||||
|
||||
return -ETIMEDOUT;
|
||||
return -ETIMEDOUT;
|
||||
}
|
||||
|
||||
static int pca9541_release_chan(struct i2c_mux_core *muxc, u32 chan)
|
||||
{
|
||||
struct pca9541 *data = i2c_mux_priv(muxc);
|
||||
struct i2c_client *client = data->client;
|
||||
pca9541_release_bus(client);
|
||||
return 0;
|
||||
struct i2c_client *client = data->client;
|
||||
pca9541_release_bus(client);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Arbitration management functions
|
||||
*/
|
||||
* Arbitration management functions
|
||||
*/
|
||||
static void pca9641_release_bus(struct i2c_client *client)
|
||||
{
|
||||
pca9541_reg_write(client, PCA9641_CONTROL, 0x80); //master 0x80
|
||||
pca9541_reg_write(client, PCA9641_CONTROL, 0x80); //master 0x80
|
||||
}
|
||||
|
||||
/*
|
||||
* Channel arbitration
|
||||
*
|
||||
* Return values:
|
||||
* <0: error
|
||||
* 0 : bus not acquired
|
||||
* 1 : bus acquired
|
||||
*/
|
||||
* Channel arbitration
|
||||
*
|
||||
* Return values:
|
||||
* <0: error
|
||||
* 0 : bus not acquired
|
||||
* 1 : bus acquired
|
||||
*/
|
||||
static int pca9641_arbitrate(struct i2c_client *client)
|
||||
{
|
||||
struct i2c_mux_core *muxc = i2c_get_clientdata(client);
|
||||
struct pca9541 *data = i2c_mux_priv(muxc);
|
||||
int reg_ctl, reg_sts;
|
||||
struct i2c_mux_core *muxc = i2c_get_clientdata(client);
|
||||
struct pca9541 *data = i2c_mux_priv(muxc);
|
||||
int reg_ctl, reg_sts;
|
||||
|
||||
reg_ctl = pca9541_reg_read(client, PCA9641_CONTROL);
|
||||
if (reg_ctl < 0)
|
||||
return reg_ctl;
|
||||
reg_sts = pca9541_reg_read(client, PCA9641_STATUS);
|
||||
reg_ctl = pca9541_reg_read(client, PCA9641_CONTROL);
|
||||
if (reg_ctl < 0)
|
||||
return reg_ctl;
|
||||
reg_sts = pca9541_reg_read(client, PCA9641_STATUS);
|
||||
|
||||
if (BUSOFF(reg_ctl, reg_sts)) {
|
||||
/*
|
||||
* Bus is off. Request ownership or turn it on unless
|
||||
* other master requested ownership.
|
||||
*/
|
||||
reg_ctl |= PCA9641_CTL_LOCK_REQ;
|
||||
pca9541_reg_write(client, PCA9641_CONTROL, reg_ctl);
|
||||
reg_ctl = pca9541_reg_read(client, PCA9641_CONTROL);
|
||||
if (BUSOFF(reg_ctl, reg_sts)) {
|
||||
/*
|
||||
* Bus is off. Request ownership or turn it on unless
|
||||
* other master requested ownership.
|
||||
*/
|
||||
reg_ctl |= PCA9641_CTL_LOCK_REQ;
|
||||
pca9541_reg_write(client, PCA9641_CONTROL, reg_ctl);
|
||||
reg_ctl = pca9541_reg_read(client, PCA9641_CONTROL);
|
||||
|
||||
if (lock_grant(reg_ctl)) {
|
||||
/*
|
||||
* Other master did not request ownership,
|
||||
* or arbitration timeout expired. Take the bus.
|
||||
*/
|
||||
reg_ctl |= PCA9641_CTL_BUS_CONNECT
|
||||
| PCA9641_CTL_LOCK_REQ;
|
||||
pca9541_reg_write(client, PCA9641_CONTROL, reg_ctl);
|
||||
data->select_timeout = SELECT_DELAY_SHORT;
|
||||
if (lock_grant(reg_ctl)) {
|
||||
/*
|
||||
* Other master did not request ownership,
|
||||
* or arbitration timeout expired. Take the bus.
|
||||
*/
|
||||
reg_ctl |= PCA9641_CTL_BUS_CONNECT
|
||||
| PCA9641_CTL_LOCK_REQ;
|
||||
pca9541_reg_write(client, PCA9641_CONTROL, reg_ctl);
|
||||
data->select_timeout = SELECT_DELAY_SHORT;
|
||||
|
||||
return 1;
|
||||
} else {
|
||||
/*
|
||||
* Other master requested ownership.
|
||||
* Set extra long timeout to give it time to acquire it.
|
||||
*/
|
||||
data->select_timeout = SELECT_DELAY_LONG * 2;
|
||||
}
|
||||
} else if (lock_grant(reg_ctl)) {
|
||||
/*
|
||||
* Bus is on, and we own it. We are done with acquisition.
|
||||
*/
|
||||
reg_ctl |= PCA9641_CTL_BUS_CONNECT | PCA9641_CTL_LOCK_REQ;
|
||||
pca9541_reg_write(client, PCA9641_CONTROL, reg_ctl);
|
||||
return 1;
|
||||
} else {
|
||||
/*
|
||||
* Other master requested ownership.
|
||||
* Set extra long timeout to give it time to acquire it.
|
||||
*/
|
||||
data->select_timeout = SELECT_DELAY_LONG * 2;
|
||||
}
|
||||
} else if (lock_grant(reg_ctl)) {
|
||||
/*
|
||||
* Bus is on, and we own it. We are done with acquisition.
|
||||
*/
|
||||
reg_ctl |= PCA9641_CTL_BUS_CONNECT | PCA9641_CTL_LOCK_REQ;
|
||||
pca9541_reg_write(client, PCA9641_CONTROL, reg_ctl);
|
||||
|
||||
return 1;
|
||||
} else if (other_lock(reg_sts)) {
|
||||
/*
|
||||
* Other master owns the bus.
|
||||
* If arbitration timeout has expired, force ownership.
|
||||
* Otherwise request it.
|
||||
*/
|
||||
data->select_timeout = SELECT_DELAY_LONG;
|
||||
reg_ctl |= PCA9641_CTL_LOCK_REQ;
|
||||
pca9541_reg_write(client, PCA9641_CONTROL, reg_ctl);
|
||||
}
|
||||
return 0;
|
||||
return 1;
|
||||
} else if (other_lock(reg_sts)) {
|
||||
/*
|
||||
* Other master owns the bus.
|
||||
* If arbitration timeout has expired, force ownership.
|
||||
* Otherwise request it.
|
||||
*/
|
||||
data->select_timeout = SELECT_DELAY_LONG;
|
||||
reg_ctl |= PCA9641_CTL_LOCK_REQ;
|
||||
pca9541_reg_write(client, PCA9641_CONTROL, reg_ctl);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
int pca9641_select_chan(struct i2c_mux_core *muxc, u32 chan)
|
||||
{
|
||||
struct pca9541 *data = i2c_mux_priv(muxc);
|
||||
struct pca9541 *data = i2c_mux_priv(muxc);
|
||||
struct i2c_client *client = data->client;
|
||||
int ret;
|
||||
int result;
|
||||
@ -472,42 +472,42 @@ int pca9641_select_chan(struct i2c_mux_core *muxc, u32 chan)
|
||||
/* give up after this time */
|
||||
data->arb_timeout = jiffies + ARB_TIMEOUT;
|
||||
/* force bus ownership after this time */
|
||||
for (result = 0 ; result < PCA9641_RETRY_TIME ; result ++) {
|
||||
do {
|
||||
ret = pca9641_arbitrate(client);
|
||||
if (ret == 1) {
|
||||
return 0;
|
||||
}
|
||||
if (data->select_timeout == SELECT_DELAY_SHORT)
|
||||
udelay(data->select_timeout);
|
||||
else
|
||||
msleep(data->select_timeout / 1000);
|
||||
} while (time_is_after_eq_jiffies(timeout));
|
||||
timeout = jiffies + ARB2_TIMEOUT;
|
||||
}
|
||||
for (result = 0 ; result < PCA9641_RETRY_TIME ; result ++) {
|
||||
do {
|
||||
ret = pca9641_arbitrate(client);
|
||||
if (ret == 1) {
|
||||
return 0;
|
||||
}
|
||||
if (data->select_timeout == SELECT_DELAY_SHORT)
|
||||
udelay(data->select_timeout);
|
||||
else
|
||||
msleep(data->select_timeout / 1000);
|
||||
} while (time_is_after_eq_jiffies(timeout));
|
||||
timeout = jiffies + ARB2_TIMEOUT;
|
||||
}
|
||||
return -ETIMEDOUT;
|
||||
}
|
||||
EXPORT_SYMBOL(pca9641_select_chan);
|
||||
|
||||
static int pca9641_release_chan(struct i2c_mux_core *muxc, u32 chan)
|
||||
{
|
||||
struct pca9541 *data = i2c_mux_priv(muxc);
|
||||
struct i2c_client *client = data->client;
|
||||
if (pca_flag.flag) {
|
||||
pca9641_release_bus(client);
|
||||
}
|
||||
return 0;
|
||||
struct pca9541 *data = i2c_mux_priv(muxc);
|
||||
struct i2c_client *client = data->client;
|
||||
if (pca_flag.flag) {
|
||||
pca9641_release_bus(client);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int pca9641_detect_id(struct i2c_client *client)
|
||||
{
|
||||
int reg;
|
||||
int reg;
|
||||
|
||||
reg = pca9541_reg_read(client, PCA9641_ID);
|
||||
if (reg == PCA9641_ID_MAGIC)
|
||||
return 1;
|
||||
else
|
||||
return 0;
|
||||
reg = pca9541_reg_read(client, PCA9641_ID);
|
||||
if (reg == PCA9641_ID_MAGIC)
|
||||
return 1;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@ -517,51 +517,51 @@ static int pca9641_recordflag(struct i2c_adapter *adap) {
|
||||
return -1 ;
|
||||
}
|
||||
pca_flag.nr = adap->nr;
|
||||
PCA_DEBUG(" adap->nr:%d\n", adap->nr);
|
||||
snprintf(pca_flag.name, sizeof(pca_flag.name),adap->name);
|
||||
PCA_DEBUG(" adap->nr:%d\n", adap->nr);
|
||||
snprintf(pca_flag.name, sizeof(pca_flag.name),adap->name);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void i2c_lock_adapter(struct i2c_adapter *adapter){
|
||||
struct i2c_adapter *parent = i2c_parent_is_i2c_adapter(adapter);
|
||||
if (parent)
|
||||
i2c_lock_adapter(parent);
|
||||
else
|
||||
rt_mutex_lock(&adapter->bus_lock);
|
||||
struct i2c_adapter *parent = i2c_parent_is_i2c_adapter(adapter);
|
||||
if (parent)
|
||||
i2c_lock_adapter(parent);
|
||||
else
|
||||
rt_mutex_lock(&adapter->bus_lock);
|
||||
}
|
||||
|
||||
void i2c_unlock_adapter(struct i2c_adapter *adapter)
|
||||
{
|
||||
struct i2c_adapter *parent = i2c_parent_is_i2c_adapter(adapter);
|
||||
struct i2c_adapter *parent = i2c_parent_is_i2c_adapter(adapter);
|
||||
|
||||
if (parent)
|
||||
i2c_unlock_adapter(parent);
|
||||
else
|
||||
rt_mutex_unlock(&adapter->bus_lock);
|
||||
if (parent)
|
||||
i2c_unlock_adapter(parent);
|
||||
else
|
||||
rt_mutex_unlock(&adapter->bus_lock);
|
||||
}
|
||||
/*
|
||||
* I2C init/probing/exit functions
|
||||
*/
|
||||
static int pca9541_probe(struct i2c_client *client,
|
||||
const struct i2c_device_id *id)
|
||||
const struct i2c_device_id *id)
|
||||
{
|
||||
struct i2c_adapter *adap = client->adapter;
|
||||
struct pca954x_platform_data *pdata = dev_get_platdata(&client->dev);
|
||||
struct i2c_adapter *adap = client->adapter;
|
||||
struct pca954x_platform_data *pdata = dev_get_platdata(&client->dev);
|
||||
struct i2c_mux_core *muxc;
|
||||
struct pca9541 *data;
|
||||
int force;
|
||||
int ret = -ENODEV;
|
||||
struct pca9541 *data;
|
||||
int force;
|
||||
int ret = -ENODEV;
|
||||
int detect_id;
|
||||
|
||||
if (!i2c_check_functionality(adap, I2C_FUNC_SMBUS_BYTE_DATA))
|
||||
return -ENODEV;
|
||||
if (!i2c_check_functionality(adap, I2C_FUNC_SMBUS_BYTE_DATA))
|
||||
return -ENODEV;
|
||||
|
||||
detect_id = pca9641_detect_id(client);
|
||||
|
||||
/*
|
||||
* I2C accesses are unprotected here.
|
||||
* We have to lock the adapter before releasing the bus.
|
||||
*/
|
||||
/*
|
||||
* I2C accesses are unprotected here.
|
||||
* We have to lock the adapter before releasing the bus.
|
||||
*/
|
||||
if (detect_id == 0) {
|
||||
i2c_lock_adapter(adap);
|
||||
pca9541_release_bus(client);
|
||||
@ -572,68 +572,68 @@ static int pca9541_probe(struct i2c_client *client,
|
||||
i2c_unlock_adapter(adap);
|
||||
}
|
||||
|
||||
/* Create mux adapter */
|
||||
/* Create mux adapter */
|
||||
|
||||
force = 0;
|
||||
if (pdata)
|
||||
force = pdata->modes[0].adap_id;
|
||||
force = 0;
|
||||
if (pdata)
|
||||
force = pdata->modes[0].adap_id;
|
||||
|
||||
if (detect_id == 0) {
|
||||
muxc = i2c_mux_alloc(adap, &client->dev, 1, sizeof(*data),
|
||||
I2C_MUX_ARBITRATOR,
|
||||
pca9541_select_chan, pca9541_release_chan);
|
||||
if (!muxc)
|
||||
return -ENOMEM;
|
||||
I2C_MUX_ARBITRATOR,
|
||||
pca9541_select_chan, pca9541_release_chan);
|
||||
if (!muxc)
|
||||
return -ENOMEM;
|
||||
|
||||
data = i2c_mux_priv(muxc);
|
||||
data->client = client;
|
||||
data = i2c_mux_priv(muxc);
|
||||
data->client = client;
|
||||
|
||||
i2c_set_clientdata(client, muxc);
|
||||
i2c_set_clientdata(client, muxc);
|
||||
|
||||
ret = i2c_mux_add_adapter(muxc, force, 0, 0);
|
||||
if (ret)
|
||||
return ret;
|
||||
ret = i2c_mux_add_adapter(muxc, force, 0, 0);
|
||||
if (ret)
|
||||
return ret;
|
||||
} else {
|
||||
muxc = i2c_mux_alloc(adap, &client->dev, 1, sizeof(*data),
|
||||
I2C_MUX_ARBITRATOR,
|
||||
pca9641_select_chan, pca9641_release_chan);
|
||||
if (!muxc)
|
||||
return -ENOMEM;
|
||||
muxc = i2c_mux_alloc(adap, &client->dev, 1, sizeof(*data),
|
||||
I2C_MUX_ARBITRATOR,
|
||||
pca9641_select_chan, pca9641_release_chan);
|
||||
if (!muxc)
|
||||
return -ENOMEM;
|
||||
|
||||
data = i2c_mux_priv(muxc);
|
||||
data->client = client;
|
||||
data = i2c_mux_priv(muxc);
|
||||
data->client = client;
|
||||
|
||||
i2c_set_clientdata(client, muxc);
|
||||
i2c_set_clientdata(client, muxc);
|
||||
|
||||
ret = i2c_mux_add_adapter(muxc, force, 0, 0);
|
||||
if (ret)
|
||||
return ret;
|
||||
ret = i2c_mux_add_adapter(muxc, force, 0, 0);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
pca9641_recordflag(muxc->adapter[0]);
|
||||
pca9641_recordflag(muxc->adapter[0]);
|
||||
|
||||
dev_info(&client->dev, "registered master selector for I2C %s\n",
|
||||
client->name);
|
||||
dev_info(&client->dev, "registered master selector for I2C %s\n",
|
||||
client->name);
|
||||
|
||||
return 0;
|
||||
return 0;
|
||||
|
||||
}
|
||||
|
||||
static int pca9541_remove(struct i2c_client *client)
|
||||
{
|
||||
struct i2c_mux_core *muxc = i2c_get_clientdata(client);
|
||||
struct i2c_mux_core *muxc = i2c_get_clientdata(client);
|
||||
|
||||
i2c_mux_del_adapters(muxc);
|
||||
return 0;
|
||||
i2c_mux_del_adapters(muxc);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct i2c_driver pca9641_driver = {
|
||||
.driver = {
|
||||
.name = "pca9641",
|
||||
.of_match_table = of_match_ptr(pca9541_of_match),
|
||||
},
|
||||
.probe = pca9541_probe,
|
||||
.remove = pca9541_remove,
|
||||
.id_table = pca9541_id,
|
||||
.driver = {
|
||||
.name = "pca9641",
|
||||
.of_match_table = of_match_ptr(pca9541_of_match),
|
||||
},
|
||||
.probe = pca9541_probe,
|
||||
.remove = pca9541_remove,
|
||||
.id_table = pca9541_id,
|
||||
};
|
||||
|
||||
module_i2c_driver(pca9641_driver);
|
||||
|
@ -0,0 +1,837 @@
|
||||
/*
|
||||
* i2c-ocores.c: I2C bus driver for OpenCores I2C controller
|
||||
* (http://www.opencores.org/projects.cgi/web/i2c/overview).
|
||||
*
|
||||
* Peter Korsgaard <jacmet@sunsite.dk>
|
||||
*
|
||||
* Support for the GRLIB port of the controller by
|
||||
* Andreas Larsson <andreas@gaisler.com>
|
||||
*
|
||||
* This file is licensed under the terms of the GNU General Public License
|
||||
* version 2. This program is licensed "as is" without any warranty of any
|
||||
* kind, whether express or implied.
|
||||
*/
|
||||
|
||||
#include <linux/err.h>
|
||||
#include <linux/kernel.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/errno.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/i2c.h>
|
||||
#include <linux/interrupt.h>
|
||||
#include <linux/wait.h>
|
||||
#include <linux/slab.h>
|
||||
#include <linux/io.h>
|
||||
#include <linux/log2.h>
|
||||
#include <linux/hwmon.h>
|
||||
#include <linux/hwmon-sysfs.h>
|
||||
#include <lpc_cpld_i2c_ocores.h>
|
||||
#include <linux/spinlock.h>
|
||||
#include <linux/delay.h>
|
||||
#include <linux/jiffies.h>
|
||||
|
||||
#define OCORES_FLAG_POLL BIT(0)
|
||||
|
||||
struct ocores_i2c {
|
||||
void __iomem *base;
|
||||
u32 reg_shift;
|
||||
u32 reg_io_width;
|
||||
unsigned long flags;
|
||||
wait_queue_head_t wait;
|
||||
struct i2c_adapter adap;
|
||||
struct i2c_msg *msg;
|
||||
int pos;
|
||||
int nmsgs;
|
||||
int state; /* see STATE_ */
|
||||
spinlock_t process_lock;
|
||||
int clock_khz;
|
||||
void (*setreg)(struct ocores_i2c *i2c, int reg, u8 value);
|
||||
u8 (*getreg)(struct ocores_i2c *i2c, int reg);
|
||||
};
|
||||
|
||||
/* registers */
|
||||
#define OCI2C_PRELOW 0x0
|
||||
#define OCI2C_PREHIGH 0x1
|
||||
#define OCI2C_CONTROL 0x2
|
||||
#define OCI2C_DATA 0x3
|
||||
#define OCI2C_CMD 0x4 /* write only */
|
||||
#define OCI2C_STATUS 0x4 /* read only, same address as OCI2C_CMD */
|
||||
|
||||
#define OCI2C_TRAN_REV 0x14
|
||||
#define OCI2C_CMD_REV 0x18
|
||||
|
||||
|
||||
#define OCI2C_CTRL_IEN 0x40
|
||||
#define OCI2C_CTRL_EN 0x80
|
||||
|
||||
#define OCI2C_CMD_START 0x91
|
||||
#define OCI2C_CMD_STOP 0x41
|
||||
#define OCI2C_CMD_READ 0x21
|
||||
#define OCI2C_CMD_WRITE 0x11
|
||||
#define OCI2C_CMD_READ_ACK 0x21
|
||||
#define OCI2C_CMD_READ_NACK 0x29
|
||||
#define OCI2C_CMD_IACK 0x01
|
||||
|
||||
#define OCI2C_STAT_IF 0x01
|
||||
#define OCI2C_STAT_TIP 0x02
|
||||
#define OCI2C_STAT_ARBLOST 0x20
|
||||
#define OCI2C_STAT_BUSY 0x40
|
||||
#define OCI2C_STAT_NACK 0x80
|
||||
|
||||
#define STATE_DONE 0
|
||||
#define STATE_START 1
|
||||
#define STATE_WRITE 2
|
||||
#define STATE_READ 3
|
||||
#define STATE_ERROR 4
|
||||
|
||||
#define TYPE_OCORES 0
|
||||
#define TYPE_GRLIB 1
|
||||
#define OCI2C_WAIT_SLEEP 40
|
||||
|
||||
int g_lpc_cpld_i2c_debug = 0;
|
||||
int g_lpc_cpld_i2c_irq = 0;
|
||||
int g_lpc_cpld_i2c_error = 0;
|
||||
|
||||
module_param(g_lpc_cpld_i2c_debug, int, S_IRUGO | S_IWUSR);
|
||||
module_param(g_lpc_cpld_i2c_error, int, S_IRUGO | S_IWUSR);
|
||||
module_param(g_lpc_cpld_i2c_irq, int, S_IRUGO | S_IWUSR);
|
||||
|
||||
int g_irq_dump_debug = 0;
|
||||
module_param(g_irq_dump_debug, int, S_IRUGO | S_IWUSR);
|
||||
#define LPC_CPLD_I2C_DEBUG_DUMP(fmt, args...) do { \
|
||||
if (g_irq_dump_debug) { \
|
||||
printk(KERN_ERR ""fmt, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
int g_irq_invalid_cnt = 0;
|
||||
module_param(g_irq_invalid_cnt, int, S_IRUGO | S_IWUSR);
|
||||
#define LPC_CPLD_I2C_DEBUG_XFER(fmt, args...) do { \
|
||||
if (g_lpc_cpld_i2c_irq) { \
|
||||
printk(KERN_ERR "[LPC_CPLD_I2C_OCORES][XFER][func:%s line:%d]\r\n"fmt, __func__, __LINE__, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define LPC_CPLD_I2C_DEBUG_VERBOSE(fmt, args...) do { \
|
||||
if (g_lpc_cpld_i2c_debug) { \
|
||||
printk(KERN_ERR "[LPC_CPLD_I2C_OCORES][VER][func:%s line:%d]\r\n"fmt, __func__, __LINE__, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define LPC_CPLD_I2C_DEBUG_ERROR(fmt, args...) do { \
|
||||
if (g_lpc_cpld_i2c_error) { \
|
||||
printk(KERN_ERR "[LPC_CPLD_I2C_OCORES][ERR][func:%s line:%d]\r\n"fmt, __func__, __LINE__, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
static int g_lpc_cpld_i2c_irq_flag = 1;
|
||||
|
||||
module_param(g_lpc_cpld_i2c_irq_flag, int, S_IRUGO | S_IWUSR);
|
||||
|
||||
static void oc_debug_dump_reg(struct ocores_i2c *i2c);
|
||||
static void oc_setreg_8(struct ocores_i2c *i2c, int reg, u8 value)
|
||||
{
|
||||
u64 base = (u64)i2c->base;
|
||||
|
||||
outb(value, (u16)base + reg);
|
||||
}
|
||||
|
||||
static inline u8 oc_getreg_8(struct ocores_i2c *i2c, int reg)
|
||||
{
|
||||
u64 base = (u64)i2c->base;
|
||||
|
||||
return inb((u16)base + reg);
|
||||
}
|
||||
|
||||
static inline void oc_setreg(struct ocores_i2c *i2c, int reg, u8 value)
|
||||
{
|
||||
i2c->setreg(i2c, reg, value);
|
||||
}
|
||||
|
||||
static inline u8 oc_getreg(struct ocores_i2c *i2c, int reg)
|
||||
{
|
||||
u8 status;
|
||||
|
||||
status = i2c->getreg(i2c, reg);
|
||||
return status;
|
||||
}
|
||||
|
||||
#define LPC_CPLD_I2C_SPIN_LOCK(lock, flags) spin_lock_irqsave(&(lock), (flags))
|
||||
#define LPC_CPLD_I2C_SPIN_UNLOCK(lock, flags) spin_unlock_irqrestore(&(lock), (flags))
|
||||
|
||||
static void ocores_process(struct ocores_i2c *i2c, u8 stat)
|
||||
{
|
||||
struct i2c_msg *msg = i2c->msg;
|
||||
|
||||
LPC_CPLD_I2C_DEBUG_XFER("Enter nr %d.\n", i2c->adap.nr);
|
||||
|
||||
/*
|
||||
* If we spin here is because we are in timeout, so we are going
|
||||
* to be in STATE_ERROR. See ocores_process_timeout()
|
||||
*/
|
||||
if ((i2c->state == STATE_DONE) || (i2c->state == STATE_ERROR)) {
|
||||
/* stop has been sent */
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_IACK);
|
||||
wake_up(&i2c->wait);
|
||||
LPC_CPLD_I2C_DEBUG_XFER("stop has been sent, exit.\n");
|
||||
goto out;
|
||||
}
|
||||
|
||||
/* error */
|
||||
if (stat & OCI2C_STAT_ARBLOST) {
|
||||
i2c->state = STATE_ERROR;
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_STOP);
|
||||
LPC_CPLD_I2C_DEBUG_XFER("error, exit.\n");
|
||||
goto out;
|
||||
}
|
||||
|
||||
if ((i2c->state == STATE_START) || (i2c->state == STATE_WRITE)) {
|
||||
i2c->state =
|
||||
(msg->flags & I2C_M_RD) ? STATE_READ : STATE_WRITE;
|
||||
|
||||
if (stat & OCI2C_STAT_NACK) {
|
||||
i2c->state = STATE_ERROR;
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_STOP);
|
||||
LPC_CPLD_I2C_DEBUG_XFER("OCI2C_STAT_NACK, exit.\n");
|
||||
goto out;
|
||||
}
|
||||
} else
|
||||
msg->buf[i2c->pos++] = oc_getreg(i2c, OCI2C_DATA);
|
||||
|
||||
/* end of msg */
|
||||
if (i2c->pos == msg->len) {
|
||||
LPC_CPLD_I2C_DEBUG_XFER("Enter end of msg.\n");
|
||||
i2c->nmsgs--;
|
||||
i2c->msg++;
|
||||
i2c->pos = 0;
|
||||
msg = i2c->msg;
|
||||
|
||||
if (i2c->nmsgs) { /* end? */
|
||||
/* send start */
|
||||
if (!(msg->flags & I2C_M_NOSTART)) {
|
||||
u8 addr = (msg->addr << 1);
|
||||
|
||||
if (msg->flags & I2C_M_RD)
|
||||
addr |= 1;
|
||||
|
||||
i2c->state = STATE_START;
|
||||
|
||||
oc_setreg(i2c, OCI2C_DATA, addr);
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_START);
|
||||
LPC_CPLD_I2C_DEBUG_XFER("send start, exit.\n");
|
||||
goto out;
|
||||
}
|
||||
|
||||
i2c->state = (msg->flags & I2C_M_RD)
|
||||
? STATE_READ : STATE_WRITE;
|
||||
} else {
|
||||
i2c->state = STATE_DONE;
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_STOP);
|
||||
LPC_CPLD_I2C_DEBUG_XFER("send OCI2C_CMD_STOP, exit.\n");
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
|
||||
if (i2c->state == STATE_READ) {
|
||||
oc_setreg(i2c, OCI2C_CMD, i2c->pos == (msg->len-1) ?
|
||||
OCI2C_CMD_READ_NACK : OCI2C_CMD_READ_ACK);
|
||||
} else {
|
||||
oc_setreg(i2c, OCI2C_DATA, msg->buf[i2c->pos++]);
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_WRITE);
|
||||
}
|
||||
|
||||
out:
|
||||
LPC_CPLD_I2C_DEBUG_XFER("normal, exit nr %d.\n", i2c->adap.nr);
|
||||
}
|
||||
|
||||
static irqreturn_t ocores_isr(int irq, void *dev_id)
|
||||
{
|
||||
struct ocores_i2c *i2c = dev_id;
|
||||
unsigned long flags;
|
||||
u8 stat;
|
||||
if (!i2c) {
|
||||
return IRQ_NONE;
|
||||
}
|
||||
|
||||
LPC_CPLD_I2C_SPIN_LOCK(i2c->process_lock, flags);
|
||||
stat = oc_getreg(i2c, OCI2C_STATUS);
|
||||
|
||||
if (!(stat & OCI2C_STAT_IF)) {
|
||||
g_irq_invalid_cnt++;
|
||||
LPC_CPLD_I2C_SPIN_UNLOCK(i2c->process_lock, flags);
|
||||
return IRQ_NONE;
|
||||
}
|
||||
|
||||
LPC_CPLD_I2C_DEBUG_XFER("Enter, irq %d nr %d addr 0x%x.\n", irq, i2c->adap.nr, i2c->msg->addr);
|
||||
ocores_process(i2c, stat);
|
||||
LPC_CPLD_I2C_DEBUG_XFER("Leave, irq %d nr %d addr 0x%x.\n", irq, i2c->adap.nr, i2c->msg->addr);
|
||||
LPC_CPLD_I2C_SPIN_UNLOCK(i2c->process_lock, flags);
|
||||
|
||||
return IRQ_HANDLED;
|
||||
}
|
||||
|
||||
/**
|
||||
* Process timeout event
|
||||
* @i2c: ocores I2C device instance
|
||||
*/
|
||||
static void ocores_process_timeout(struct ocores_i2c *i2c)
|
||||
{
|
||||
unsigned long flags;
|
||||
|
||||
LPC_CPLD_I2C_SPIN_LOCK(i2c->process_lock, flags);
|
||||
i2c->state = STATE_ERROR;
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_STOP);
|
||||
mdelay(1);
|
||||
LPC_CPLD_I2C_SPIN_UNLOCK(i2c->process_lock, flags);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Wait until something change in a given register
|
||||
* @i2c: ocores I2C device instance
|
||||
* @reg: register to query
|
||||
* @mask: bitmask to apply on register value
|
||||
* @val: expected result
|
||||
* @timeout: timeout in jiffies
|
||||
*
|
||||
* Timeout is necessary to avoid to stay here forever when the chip
|
||||
* does not answer correctly.
|
||||
*
|
||||
* Return: 0 on success, -ETIMEDOUT on timeout
|
||||
*/
|
||||
static int ocores_wait(struct ocores_i2c *i2c,
|
||||
int reg, u8 mask, u8 val,
|
||||
const unsigned long timeout)
|
||||
{
|
||||
u8 status;
|
||||
unsigned long j, jiffies_tmp;
|
||||
unsigned int usleep;
|
||||
usleep = OCI2C_WAIT_SLEEP;
|
||||
j = jiffies + timeout;
|
||||
while (1) {
|
||||
jiffies_tmp = jiffies;
|
||||
status = oc_getreg(i2c, reg);
|
||||
|
||||
if ((status & mask) == val)
|
||||
break;
|
||||
|
||||
if (time_after(jiffies_tmp, j)) {
|
||||
LPC_CPLD_I2C_DEBUG_XFER("STATUS timeout, mask[0x%x] val[0x%x] status[0x%x]\n", mask, val, status);
|
||||
return -ETIMEDOUT;
|
||||
}
|
||||
usleep_range(usleep,usleep + 1);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Wait until is possible to process some data
|
||||
* @i2c: ocores I2C device instance
|
||||
*
|
||||
* Used when the device is in polling mode (interrupts disabled).
|
||||
*
|
||||
* Return: 0 on success, -ETIMEDOUT on timeout
|
||||
*/
|
||||
static int ocores_poll_wait(struct ocores_i2c *i2c)
|
||||
{
|
||||
u8 mask;
|
||||
int err;
|
||||
|
||||
if (i2c->state == STATE_DONE || i2c->state == STATE_ERROR) {
|
||||
/* transfer is over */
|
||||
mask = OCI2C_STAT_BUSY;
|
||||
} else {
|
||||
/* on going transfer */
|
||||
mask = OCI2C_STAT_TIP;
|
||||
udelay((8 * 1000) / i2c->clock_khz);
|
||||
}
|
||||
|
||||
/*
|
||||
* once we are here we expect to get the expected result immediately
|
||||
* so if after 1ms we timeout then something is broken.
|
||||
*/
|
||||
err = ocores_wait(i2c, OCI2C_STATUS, mask, 0, msecs_to_jiffies(100));
|
||||
if (err) {
|
||||
LPC_CPLD_I2C_DEBUG_XFER("STATUS timeout, bit 0x%x did not clear in 1ms, err %d\n", mask, err);
|
||||
}
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* It handles an IRQ-less transfer
|
||||
* @i2c: ocores I2C device instance
|
||||
*
|
||||
* Even if IRQ are disabled, the I2C OpenCore IP behavior is exactly the same
|
||||
* (only that IRQ are not produced). This means that we can re-use entirely
|
||||
* ocores_isr(), we just add our polling code around it.
|
||||
*
|
||||
* It can run in atomic context
|
||||
*/
|
||||
static int ocores_process_polling(struct ocores_i2c *i2c)
|
||||
{
|
||||
irqreturn_t ret;
|
||||
int err;
|
||||
while (1) {
|
||||
err = ocores_poll_wait(i2c);
|
||||
if (err) {
|
||||
i2c->state = STATE_ERROR;
|
||||
break; /* timeout */
|
||||
}
|
||||
|
||||
ret = ocores_isr(-1, i2c);
|
||||
if (ret == IRQ_NONE)
|
||||
break; /* all messages have been transfered */
|
||||
}
|
||||
return err;
|
||||
}
|
||||
|
||||
static int ocores_xfer_core(struct ocores_i2c *i2c,
|
||||
struct i2c_msg *msgs, int num,
|
||||
bool polling)
|
||||
{
|
||||
int ret;
|
||||
unsigned long flags;
|
||||
u8 ctrl;
|
||||
|
||||
LPC_CPLD_I2C_DEBUG_XFER("Enter.polling %d\n", polling);
|
||||
LPC_CPLD_I2C_SPIN_LOCK(i2c->process_lock, flags);
|
||||
ctrl = oc_getreg(i2c, OCI2C_CONTROL);
|
||||
if (polling)
|
||||
oc_setreg(i2c, OCI2C_CONTROL, ctrl & ~OCI2C_CTRL_IEN);
|
||||
else
|
||||
oc_setreg(i2c, OCI2C_CONTROL, ctrl | OCI2C_CTRL_IEN);
|
||||
|
||||
i2c->msg = msgs;
|
||||
i2c->pos = 0;
|
||||
i2c->nmsgs = num;
|
||||
i2c->state = STATE_START;
|
||||
|
||||
oc_setreg(i2c, OCI2C_DATA,
|
||||
(i2c->msg->addr << 1) |
|
||||
((i2c->msg->flags & I2C_M_RD) ? 1:0));
|
||||
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_START);
|
||||
LPC_CPLD_I2C_SPIN_UNLOCK(i2c->process_lock, flags);
|
||||
|
||||
if (polling) {
|
||||
ret = ocores_process_polling(i2c);
|
||||
if (ret) { /* timeout */
|
||||
ocores_process_timeout(i2c);
|
||||
return -ETIMEDOUT;
|
||||
}
|
||||
} else {
|
||||
ret = wait_event_timeout(i2c->wait,
|
||||
(i2c->state == STATE_ERROR) ||
|
||||
(i2c->state == STATE_DONE), HZ);
|
||||
if (ret == 0) {
|
||||
ocores_process_timeout(i2c);
|
||||
return -ETIMEDOUT;
|
||||
}
|
||||
}
|
||||
|
||||
return (i2c->state == STATE_DONE) ? num : -EIO;
|
||||
}
|
||||
|
||||
static int ocores_xfer_polling(struct i2c_adapter *adap,
|
||||
struct i2c_msg *msgs, int num)
|
||||
{
|
||||
LPC_CPLD_I2C_DEBUG_XFER("Enter.\n");
|
||||
return ocores_xfer_core(i2c_get_adapdata(adap), msgs, num, true);
|
||||
}
|
||||
|
||||
static int ocores_xfer(struct i2c_adapter *adap,
|
||||
struct i2c_msg *msgs, int num)
|
||||
{
|
||||
struct ocores_i2c *i2c = i2c_get_adapdata(adap);
|
||||
|
||||
if (i2c->flags & OCORES_FLAG_POLL)
|
||||
return ocores_xfer_polling(adap, msgs, num);
|
||||
return ocores_xfer_core(i2c, msgs, num, false);
|
||||
}
|
||||
|
||||
static void ocores_init(struct ocores_i2c *i2c)
|
||||
{
|
||||
int prescale;
|
||||
u8 ctrl = oc_getreg(i2c, OCI2C_CONTROL);
|
||||
|
||||
LPC_CPLD_I2C_DEBUG_XFER("Enter.\n");
|
||||
spin_lock_init(&i2c->process_lock);
|
||||
|
||||
/* make sure the device is disabled */
|
||||
oc_setreg(i2c, OCI2C_CONTROL, ctrl & ~(OCI2C_CTRL_EN|OCI2C_CTRL_IEN));
|
||||
|
||||
prescale = (i2c->clock_khz / (5*100)) - 1;
|
||||
oc_setreg(i2c, OCI2C_PRELOW, prescale & 0xff);
|
||||
oc_setreg(i2c, OCI2C_PREHIGH, prescale >> 8);
|
||||
LPC_CPLD_I2C_DEBUG_VERBOSE("i2c->base 0x%p, i2c->clock_khz %d, prescale 0x%x.\n", i2c->base, i2c->clock_khz, prescale);
|
||||
|
||||
/* Init the device */
|
||||
oc_setreg(i2c, OCI2C_CMD, OCI2C_CMD_IACK);
|
||||
oc_setreg(i2c, OCI2C_CONTROL, ctrl | OCI2C_CTRL_EN);
|
||||
}
|
||||
|
||||
|
||||
static u32 ocores_func(struct i2c_adapter *adap)
|
||||
{
|
||||
return I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL;
|
||||
}
|
||||
|
||||
static const struct i2c_algorithm ocores_algorithm = {
|
||||
.master_xfer = ocores_xfer,
|
||||
.functionality = ocores_func,
|
||||
};
|
||||
|
||||
static struct i2c_adapter ocores_adapter = {
|
||||
.owner = THIS_MODULE,
|
||||
.name = "rg-cpld-ocrore-i2c",
|
||||
.class = I2C_CLASS_HWMON | I2C_CLASS_SPD | I2C_CLASS_DEPRECATED,
|
||||
.algo = &ocores_algorithm,
|
||||
};
|
||||
|
||||
static const struct of_device_id ocores_i2c_match[] = {
|
||||
{
|
||||
.compatible = "opencores,rg-cpld-ocrore-i2c",
|
||||
.data = (void *)TYPE_OCORES,
|
||||
},
|
||||
{},
|
||||
};
|
||||
MODULE_DEVICE_TABLE(of, ocores_i2c_match);
|
||||
|
||||
#ifdef CONFIG_OF
|
||||
/* Read and write functions for the GRLIB port of the controller. Registers are
|
||||
* 32-bit big endian and the PRELOW and PREHIGH registers are merged into one
|
||||
* register. The subsequent registers has their offset decreased accordingly. */
|
||||
static u8 oc_getreg_grlib(struct ocores_i2c *i2c, int reg)
|
||||
{
|
||||
u32 rd;
|
||||
int rreg = reg;
|
||||
if (reg != OCI2C_PRELOW)
|
||||
rreg--;
|
||||
rd = ioread32be(i2c->base + (rreg << i2c->reg_shift));
|
||||
if (reg == OCI2C_PREHIGH)
|
||||
return (u8)(rd >> 8);
|
||||
else
|
||||
return (u8)rd;
|
||||
}
|
||||
|
||||
static void oc_setreg_grlib(struct ocores_i2c *i2c, int reg, u8 value)
|
||||
{
|
||||
u32 curr, wr;
|
||||
int rreg = reg;
|
||||
if (reg != OCI2C_PRELOW)
|
||||
rreg--;
|
||||
if (reg == OCI2C_PRELOW || reg == OCI2C_PREHIGH) {
|
||||
curr = ioread32be(i2c->base + (rreg << i2c->reg_shift));
|
||||
if (reg == OCI2C_PRELOW)
|
||||
wr = (curr & 0xff00) | value;
|
||||
else
|
||||
wr = (((u32)value) << 8) | (curr & 0xff);
|
||||
} else {
|
||||
wr = value;
|
||||
}
|
||||
iowrite32be(wr, i2c->base + (rreg << i2c->reg_shift));
|
||||
}
|
||||
|
||||
static int ocores_i2c_of_probe(struct platform_device *pdev,
|
||||
struct ocores_i2c *i2c)
|
||||
{
|
||||
struct device_node *np = pdev->dev.of_node;
|
||||
const struct of_device_id *match;
|
||||
u32 val;
|
||||
|
||||
LPC_CPLD_I2C_DEBUG_VERBOSE("Enter ocores_i2c_of_probe.\n");
|
||||
if (of_property_read_u32(np, "reg-shift", &i2c->reg_shift)) {
|
||||
/* no 'reg-shift', check for deprecated 'regstep' */
|
||||
if (!of_property_read_u32(np, "regstep", &val)) {
|
||||
if (!is_power_of_2(val)) {
|
||||
dev_err(&pdev->dev, "invalid regstep %d\n",
|
||||
val);
|
||||
return -EINVAL;
|
||||
}
|
||||
i2c->reg_shift = ilog2(val);
|
||||
dev_warn(&pdev->dev,
|
||||
"regstep property deprecated, use reg-shift\n");
|
||||
}
|
||||
}
|
||||
|
||||
if (of_property_read_u32(np, "clock-frequency", &val)) {
|
||||
dev_err(&pdev->dev,
|
||||
"Missing required parameter 'clock-frequency'\n");
|
||||
return -ENODEV;
|
||||
}
|
||||
i2c->clock_khz = val / 1000;
|
||||
|
||||
of_property_read_u32(pdev->dev.of_node, "reg-io-width",
|
||||
&i2c->reg_io_width);
|
||||
|
||||
match = of_match_node(ocores_i2c_match, pdev->dev.of_node);
|
||||
if (match && (long)match->data == TYPE_GRLIB) {
|
||||
dev_dbg(&pdev->dev, "GRLIB variant of i2c-ocores\n");
|
||||
i2c->setreg = oc_setreg_grlib;
|
||||
i2c->getreg = oc_getreg_grlib;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
#else
|
||||
#define ocores_i2c_of_probe(pdev,i2c) -ENODEV
|
||||
#endif
|
||||
|
||||
static void oc_debug_dump_reg(struct ocores_i2c *i2c)
|
||||
{
|
||||
if (i2c) {
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("base: %p.\n", i2c->base);
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("reg_shift: %d.\n", i2c->reg_shift);
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("reg_io_width: %d.\n", i2c->reg_io_width);
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("adap.nr: %d.\n", i2c->adap.nr);
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("msg: %p.\n", i2c->msg);
|
||||
if (i2c->msg) {
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("msg->buf: %p.\n", i2c->msg->buf);
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("msg->addr: 0x%x.\n", i2c->msg->addr);
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("msg->flags: 0x%x.\n", i2c->msg->flags);
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("msg->len: %d.\n", i2c->msg->len);
|
||||
} else {
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("msg: %p is null.\n", i2c->msg);
|
||||
}
|
||||
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("pos: %d.\n", i2c->pos);
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("nmsgs: %d.\n", i2c->nmsgs);
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("state: %d.\n", i2c->state);
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("clock_khz: %d.\n", i2c->clock_khz);
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("setreg: %p.\n", i2c->setreg);
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("getreg: %p.\n", i2c->getreg);
|
||||
if (i2c->getreg) {
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("OCI2C_PRELOW: 0x%02x.\n", oc_getreg(i2c, OCI2C_PRELOW));
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("OCI2C_PREHIGH: 0x%02x.\n", oc_getreg(i2c, OCI2C_PREHIGH));
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("OCI2C_CONTROL: 0x%02x.\n", oc_getreg(i2c, OCI2C_CONTROL));
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("OCI2C_DATA: 0x%02x.\n", oc_getreg(i2c, OCI2C_DATA));
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("OCI2C_CMD: 0x%02x.\n", oc_getreg(i2c, OCI2C_CMD));
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("OCI2C_STATUS: 0x%02x.\n", oc_getreg(i2c, OCI2C_STATUS));
|
||||
} else {
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("getreg: %p is null.\n", i2c->getreg);
|
||||
}
|
||||
} else {
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("i2c %p is null.\n", i2c);
|
||||
}
|
||||
}
|
||||
|
||||
void oc_debug_dump_reg_exception(void)
|
||||
{
|
||||
int bus_beg, bus_end, bus;
|
||||
struct i2c_adapter *adap;
|
||||
struct ocores_i2c *adap_data;
|
||||
|
||||
bus_beg = 1;
|
||||
bus_end = 14;
|
||||
for (bus = bus_beg; bus <= bus_end; bus++) {
|
||||
adap = i2c_get_adapter(bus);
|
||||
if (adap) {
|
||||
adap_data = (struct ocores_i2c *)i2c_get_adapdata(adap);
|
||||
if (adap_data) {
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("bus %d call oc_debug_dump_reg begin.\n", bus);
|
||||
oc_debug_dump_reg(adap_data);
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("bus %d call oc_debug_dump_reg end.\n", bus);
|
||||
} else {
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("bus %d i2c_get_adapdata null.\n", bus);
|
||||
}
|
||||
i2c_put_adapter(adap);
|
||||
} else {
|
||||
LPC_CPLD_I2C_DEBUG_DUMP("bus %d i2c_get_adapter null.\n", bus);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static ssize_t show_oc_debug_value(struct device *dev, struct device_attribute *da, char *buf)
|
||||
{
|
||||
oc_debug_dump_reg_exception();
|
||||
return 0;
|
||||
}
|
||||
|
||||
static SENSOR_DEVICE_ATTR(oc_debug, S_IRUGO | S_IWUSR, show_oc_debug_value, NULL, 0x15);
|
||||
|
||||
static struct attribute *oc_debug_sysfs_attrs[] = {
|
||||
&sensor_dev_attr_oc_debug.dev_attr.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
static const struct attribute_group oc_debug_sysfs_group = {
|
||||
.attrs = oc_debug_sysfs_attrs,
|
||||
};
|
||||
|
||||
static void oc_debug_sysfs_init(struct platform_device *pdev)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret = sysfs_create_group(&pdev->dev.kobj, &oc_debug_sysfs_group);
|
||||
LPC_CPLD_I2C_DEBUG_VERBOSE("sysfs_create_group ret %d.\n", ret);
|
||||
return;
|
||||
}
|
||||
|
||||
static void oc_debug_sysfs_exit(struct platform_device *pdev)
|
||||
{
|
||||
sysfs_remove_group(&pdev->dev.kobj, (const struct attribute_group *)&oc_debug_sysfs_group);
|
||||
LPC_CPLD_I2C_DEBUG_VERBOSE("sysfs_remove_group.\n");
|
||||
return;
|
||||
}
|
||||
|
||||
static int rg_ocores_i2c_probe(struct platform_device *pdev)
|
||||
{
|
||||
struct ocores_i2c *i2c;
|
||||
struct rg_ocores_cpld_i2c_platform_data *pdata;
|
||||
struct resource *res;
|
||||
int irq;
|
||||
int ret;
|
||||
int i;
|
||||
|
||||
LPC_CPLD_I2C_DEBUG_VERBOSE("Enter.\n");
|
||||
|
||||
i2c = devm_kzalloc(&pdev->dev, sizeof(*i2c), GFP_KERNEL);
|
||||
if (!i2c) {
|
||||
LPC_CPLD_I2C_DEBUG_ERROR("devm_kzalloc failed.\n");
|
||||
return -ENOMEM;
|
||||
}
|
||||
res = platform_get_resource(pdev, IORESOURCE_IO, 0);
|
||||
if (!res) {
|
||||
LPC_CPLD_I2C_DEBUG_ERROR("can't fetch device resource info\n");
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
i2c->base = (void __iomem *)res->start;
|
||||
LPC_CPLD_I2C_DEBUG_VERBOSE("i2c->base is %p., res->end[%d]\n", i2c->base, (int)res->end);
|
||||
|
||||
pdata = dev_get_platdata(&pdev->dev);
|
||||
if (pdata) {
|
||||
i2c->reg_shift = pdata->reg_shift;
|
||||
i2c->reg_io_width = pdata->reg_io_width;
|
||||
i2c->clock_khz = pdata->clock_khz;
|
||||
} else {
|
||||
ret = ocores_i2c_of_probe(pdev, i2c);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
|
||||
LPC_CPLD_I2C_DEBUG_VERBOSE("data: shift[%d], width[%d], clock_khz[%d] i2c_irq_flag=%d\n",
|
||||
pdata->reg_shift, pdata->reg_io_width, pdata->clock_khz, pdata->i2c_irq_flag);
|
||||
|
||||
if (i2c->reg_io_width == 0)
|
||||
i2c->reg_io_width = 1; /* Set to default value */
|
||||
|
||||
|
||||
if (!i2c->setreg || !i2c->getreg) {
|
||||
switch (i2c->reg_io_width) {
|
||||
case 1:
|
||||
i2c->setreg = oc_setreg_8;
|
||||
i2c->getreg = oc_getreg_8;
|
||||
break;
|
||||
default:
|
||||
dev_err(&pdev->dev, "Unsupported I/O width (%d)\n",
|
||||
i2c->reg_io_width);
|
||||
return -EINVAL;
|
||||
}
|
||||
}
|
||||
|
||||
init_waitqueue_head(&i2c->wait);
|
||||
|
||||
irq = platform_get_irq(pdev, 0);
|
||||
LPC_CPLD_I2C_DEBUG_VERBOSE("get irq %d, ENXIO[%d]", irq, ENXIO);
|
||||
if (irq == -ENXIO) {
|
||||
i2c->flags |= OCORES_FLAG_POLL;
|
||||
} else if(g_lpc_cpld_i2c_irq_flag){
|
||||
ret = devm_request_irq(&pdev->dev, irq, ocores_isr, 0,
|
||||
pdev->name, i2c);
|
||||
if (ret) {
|
||||
dev_err(&pdev->dev, "Cannot claim IRQ\n");
|
||||
}
|
||||
|
||||
if(pdata->i2c_irq_flag) {
|
||||
g_lpc_cpld_i2c_irq_flag = 0;
|
||||
}
|
||||
}
|
||||
|
||||
ocores_init(i2c);
|
||||
|
||||
/* hook up driver to tree */
|
||||
platform_set_drvdata(pdev, i2c);
|
||||
i2c->adap = ocores_adapter;
|
||||
i2c_set_adapdata(&i2c->adap, i2c);
|
||||
i2c->adap.dev.parent = &pdev->dev;
|
||||
i2c->adap.dev.of_node = pdev->dev.of_node;
|
||||
|
||||
/* add i2c adapter to i2c tree */
|
||||
ret = i2c_add_adapter(&i2c->adap);
|
||||
if (ret) {
|
||||
dev_err(&pdev->dev, "Failed to add adapter\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* add in known devices to the bus */
|
||||
if (pdata) {
|
||||
LPC_CPLD_I2C_DEBUG_VERBOSE("i2c device %d.\n", pdata->num_devices);
|
||||
for (i = 0; i < pdata->num_devices; i++)
|
||||
i2c_new_device(&i2c->adap, pdata->devices + i);
|
||||
}
|
||||
|
||||
oc_debug_sysfs_init(pdev);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rg_ocores_i2c_remove(struct platform_device *pdev)
|
||||
{
|
||||
struct ocores_i2c *i2c = platform_get_drvdata(pdev);
|
||||
|
||||
/* disable i2c logic */
|
||||
oc_setreg(i2c, OCI2C_CONTROL, oc_getreg(i2c, OCI2C_CONTROL)
|
||||
& ~(OCI2C_CTRL_EN|OCI2C_CTRL_IEN));
|
||||
|
||||
/* remove adapter & data */
|
||||
i2c_del_adapter(&i2c->adap);
|
||||
oc_debug_sysfs_exit(pdev);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_PM_SLEEP
|
||||
static int ocores_i2c_suspend(struct device *dev)
|
||||
{
|
||||
struct ocores_i2c *i2c = dev_get_drvdata(dev);
|
||||
u8 ctrl = oc_getreg(i2c, OCI2C_CONTROL);
|
||||
|
||||
/* make sure the device is disabled */
|
||||
oc_setreg(i2c, OCI2C_CONTROL, ctrl & ~(OCI2C_CTRL_EN|OCI2C_CTRL_IEN));
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int ocores_i2c_resume(struct device *dev)
|
||||
{
|
||||
struct ocores_i2c *i2c = dev_get_drvdata(dev);
|
||||
|
||||
ocores_init(i2c);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static SIMPLE_DEV_PM_OPS(ocores_i2c_pm, ocores_i2c_suspend, ocores_i2c_resume);
|
||||
#define OCORES_I2C_PM (&ocores_i2c_pm)
|
||||
#else
|
||||
#define OCORES_I2C_PM NULL
|
||||
#endif
|
||||
|
||||
static struct platform_driver ocores_i2c_driver = {
|
||||
.probe = rg_ocores_i2c_probe,
|
||||
.remove = rg_ocores_i2c_remove,
|
||||
.driver = {
|
||||
.owner = THIS_MODULE,
|
||||
.name = "rg-cpld-ocrore-i2c",
|
||||
.of_match_table = ocores_i2c_match,
|
||||
.pm = OCORES_I2C_PM,
|
||||
},
|
||||
};
|
||||
|
||||
module_platform_driver(ocores_i2c_driver);
|
||||
|
||||
MODULE_AUTHOR("Peter Korsgaard <jacmet@sunsite.dk>");
|
||||
MODULE_DESCRIPTION("OpenCores I2C bus driver");
|
||||
MODULE_LICENSE("GPL");
|
||||
MODULE_ALIAS("platform:ocores-i2c");
|
@ -0,0 +1,13 @@
|
||||
#ifndef _LPC_CPLD_I2C_OCORES_H
|
||||
#define _LPC_CPLD_I2C_OCORES_H
|
||||
|
||||
struct rg_ocores_cpld_i2c_platform_data {
|
||||
u32 reg_shift; /* register offset shift value */
|
||||
u32 reg_io_width; /* register io read/write width */
|
||||
u32 clock_khz; /* input clock in kHz */
|
||||
u8 num_devices; /* number of devices in the devices list */
|
||||
u8 i2c_irq_flag;
|
||||
struct i2c_board_info const *devices; /* devices connected to the bus */
|
||||
};
|
||||
|
||||
#endif /* _LPC_CPLD_I2C_OCORES_H */
|
534
platform/broadcom/sonic-platform-modules-ragile/common/modules/lpc_dbg.c
Executable file
534
platform/broadcom/sonic-platform-modules-ragile/common/modules/lpc_dbg.c
Executable file
@ -0,0 +1,534 @@
|
||||
#include <linux/version.h>
|
||||
#if LINUX_VERSION_CODE > KERNEL_VERSION(4, 19, 0)
|
||||
#include <linux/uaccess.h>
|
||||
#endif
|
||||
|
||||
#include <asm/uaccess.h>
|
||||
#include <linux/kernel.h> /* Wd're doing kernel work */
|
||||
#include <linux/module.h> /* specifically, a module */
|
||||
#include <linux/types.h>
|
||||
#include <linux/init.h> /* Need for the macros */
|
||||
#include <linux/moduleparam.h>
|
||||
#include <linux/fs.h>
|
||||
#include <linux/ioport.h>
|
||||
#include <linux/io.h>
|
||||
#include <linux/pci.h>
|
||||
#include <linux/sched.h>
|
||||
#include <net/sock.h>
|
||||
#include <net/genetlink.h>
|
||||
#include <linux/netlink.h>
|
||||
#include <linux/miscdevice.h>
|
||||
#include "lpc_dbg.h"
|
||||
|
||||
typedef struct rg_lpc_device_s {
|
||||
u16 base;
|
||||
u16 size;
|
||||
u8 type;
|
||||
u8 id;
|
||||
u8 lpc_pci_addr;
|
||||
} rg_lpc_device_t;
|
||||
|
||||
typedef enum rg_lpc_dev_type_s {
|
||||
LPC_DEVICE_CPLD = 1,
|
||||
LPC_DEVICE_FPGA = 2,
|
||||
} rg_lpc_dev_type_t;
|
||||
|
||||
#define MAX_LPC_DEV_NUM (4)
|
||||
#define LPC_PCI_CFG_BASE(__lgir) ((0x84) + ((__lgir) * 4))
|
||||
#define MAX_CPLD_REG_SIZE (0x100)
|
||||
#define MAX_FPGA_REG_SIZE (0x100) //# fix compile actual value 0x10000
|
||||
#define LPC_GET_CPLD_ID(addr) ((addr >> 16) & 0xff)
|
||||
#define LPC_GET_CPLD_OFFSET(addr) ((addr) & 0xff)
|
||||
|
||||
int lpc_dbg_verbose = 0;
|
||||
int lpc_dbg_error = 0;
|
||||
int lpc_dbg_info = 0;
|
||||
module_param(lpc_dbg_verbose, int, S_IRUGO | S_IWUSR);
|
||||
module_param(lpc_dbg_error, int, S_IRUGO | S_IWUSR);
|
||||
module_param(lpc_dbg_info, int, S_IRUGO | S_IWUSR);
|
||||
|
||||
|
||||
#define LPC_DBG_VERBOSE(fmt, args...) do { \
|
||||
if (lpc_dbg_verbose) { \
|
||||
printk(KERN_ERR "[LPC_DBG][VERBOSE][func:%s line:%d]\r\n"fmt, __func__, __LINE__, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define LPC_DBG_ERROR(fmt, args...) do { \
|
||||
if (lpc_dbg_error) { \
|
||||
printk(KERN_ERR "[LPC_DBG][ERROR][func:%s line:%d]\r\n"fmt, __func__, __LINE__, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define LPC_DBG_INFO(fmt, args...) do { \
|
||||
if (lpc_dbg_info) { \
|
||||
printk(KERN_ERR ""fmt, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
static rg_lpc_device_t g_rg_lpc_dev_default[] = {
|
||||
{.base = 0x700, .size = MAX_CPLD_REG_SIZE, .type = LPC_DEVICE_CPLD, .id = 0, .lpc_pci_addr = 0x84},
|
||||
{.base = 0x900, .size = MAX_CPLD_REG_SIZE, .type = LPC_DEVICE_CPLD, .id = 1, .lpc_pci_addr = 0x88},
|
||||
{.base = 0xb00, .size = MAX_CPLD_REG_SIZE, .type = LPC_DEVICE_CPLD, .id = 2, .lpc_pci_addr = 0x90},
|
||||
};
|
||||
|
||||
static rg_lpc_device_t *g_rg_lpc_dev = g_rg_lpc_dev_default;
|
||||
|
||||
static rg_lpc_device_t* lpc_get_device_info(int type, int id)
|
||||
{
|
||||
int i;
|
||||
int size;
|
||||
|
||||
size = ARRAY_SIZE(g_rg_lpc_dev_default);
|
||||
for (i = 0; i < size; i++) {
|
||||
if ((g_rg_lpc_dev[i].type == type) && (g_rg_lpc_dev[i].id == id)) {
|
||||
return &g_rg_lpc_dev[i];
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
int lpc_cpld_read(int address, u8 *val)
|
||||
{
|
||||
int cpld_id;
|
||||
rg_lpc_device_t *info;
|
||||
|
||||
cpld_id = LPC_GET_CPLD_ID(address);
|
||||
info = lpc_get_device_info(LPC_DEVICE_CPLD, cpld_id);
|
||||
if (info == NULL) {
|
||||
LPC_DBG_ERROR("lpc_get_device_info addr 0x%x id %d failed.\r\n", address, cpld_id);
|
||||
return -1;
|
||||
}
|
||||
|
||||
*val = inb(info->base + LPC_GET_CPLD_OFFSET(address));
|
||||
LPC_DBG_VERBOSE("Leave info->base 0x%x, addr 0x%x, cpld_id %d, val 0x%x.\r\n", info->base, address, cpld_id, *val);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int lpc_cpld_write(int address, u8 reg_val)
|
||||
{
|
||||
int cpld_id;
|
||||
rg_lpc_device_t *info;
|
||||
|
||||
cpld_id = LPC_GET_CPLD_ID(address);
|
||||
info = lpc_get_device_info(LPC_DEVICE_CPLD, cpld_id);
|
||||
if (info == NULL) {
|
||||
LPC_DBG_ERROR("lpc_get_device_info addr 0x%x id %d failed.\r\n", address, cpld_id);
|
||||
return -1;
|
||||
}
|
||||
|
||||
outb(reg_val, info->base + LPC_GET_CPLD_OFFSET(address));
|
||||
LPC_DBG_VERBOSE("Leave info->base 0x%x, addr 0x%x, cpld_id %d, val 0x%x.\r\n", info->base, address, cpld_id, reg_val);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int lpc_fpga_read(int address, u8 *val)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
int lpc_fpga_write(int address, u8 reg_val)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
static ssize_t lpc_misc_cpld_dev_read (struct file *file, char __user *buf, size_t count,
|
||||
loff_t *offset)
|
||||
{
|
||||
int ret;
|
||||
u8 value8[MAX_CPLD_REG_SIZE];
|
||||
int i;
|
||||
|
||||
if ((count > MAX_CPLD_REG_SIZE)
|
||||
|| ((LPC_GET_CPLD_OFFSET(file->f_pos) + count) > MAX_CPLD_REG_SIZE)) {
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
for (i = 0; i < count; i++) {
|
||||
ret = lpc_cpld_read((int)(file->f_pos + i), &value8[i]);
|
||||
if (ret) {
|
||||
LPC_DBG_ERROR("lpc_cpld_read i %d addr 0x%x failed ret %d.\n",
|
||||
i, ((unsigned int)file->f_pos + i), ret);
|
||||
return i;
|
||||
}
|
||||
}
|
||||
|
||||
if (copy_to_user(buf, value8, count)) {
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
|
||||
static ssize_t lpc_misc_cpld_dev_write (struct file *file, const char __user *buf, size_t count,
|
||||
loff_t *offset)
|
||||
{
|
||||
u8 value8[MAX_CPLD_REG_SIZE];
|
||||
int i;
|
||||
int ret;
|
||||
|
||||
if ((count > MAX_CPLD_REG_SIZE)
|
||||
|| ((LPC_GET_CPLD_OFFSET(file->f_pos) + count) > MAX_CPLD_REG_SIZE)) {
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
if (copy_from_user(value8, buf, count)) {
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
for (i = 0; i < count; i++) {
|
||||
ret = lpc_cpld_write((int)(file->f_pos + i), value8[i]);
|
||||
if (ret) {
|
||||
LPC_DBG_ERROR("lpc_cpld_write i %d addr 0x%x value 0x%x failed ret %d.\n",
|
||||
i, (unsigned int)file->f_pos + i, value8[i], ret);
|
||||
return i;
|
||||
}
|
||||
}
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
|
||||
static loff_t lpc_misc_cpld_dev_llseek(struct file *file, loff_t offset, int origin)
|
||||
{
|
||||
loff_t ret;
|
||||
|
||||
#if LINUX_VERSION_CODE < KERNEL_VERSION(4,0,36)
|
||||
mutex_lock(&file->f_path.dentry->d_inode->i_mutex);
|
||||
#else
|
||||
/* do noting add tjm */
|
||||
inode_lock(file_inode(file));
|
||||
#endif
|
||||
|
||||
switch (origin) {
|
||||
case 0:
|
||||
file->f_pos = offset;
|
||||
ret = file->f_pos;
|
||||
break;
|
||||
case 1:
|
||||
file->f_pos += offset;
|
||||
ret = file->f_pos;
|
||||
break;
|
||||
default:
|
||||
ret = -EINVAL;
|
||||
}
|
||||
|
||||
#if LINUX_VERSION_CODE < KERNEL_VERSION(4,0,36)
|
||||
mutex_unlock(&file->f_path.dentry->d_inode->i_mutex);
|
||||
#else
|
||||
/* do noting add tjm */
|
||||
inode_unlock(file_inode(file));
|
||||
#endif
|
||||
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
static long lpc_misc_cpld_dev_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
static int lpc_misc_cpld_dev_open(struct inode *inode, struct file *file)
|
||||
{
|
||||
file->private_data = NULL;
|
||||
file->f_pos = 0;
|
||||
return 0;
|
||||
|
||||
}
|
||||
|
||||
static int lpc_misc_cpld_dev_release(struct inode *inode, struct file *file)
|
||||
{
|
||||
file->private_data = NULL;
|
||||
file->f_pos = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const struct file_operations lpc_misc_cpld_dev_fops = {
|
||||
.owner = THIS_MODULE,
|
||||
.llseek = lpc_misc_cpld_dev_llseek,
|
||||
.read = lpc_misc_cpld_dev_read,
|
||||
.write = lpc_misc_cpld_dev_write,
|
||||
.unlocked_ioctl = lpc_misc_cpld_dev_ioctl,
|
||||
.open = lpc_misc_cpld_dev_open,
|
||||
.release = lpc_misc_cpld_dev_release,
|
||||
};
|
||||
|
||||
static ssize_t lpc_misc_fpga_dev_read (struct file *file, char __user *buf, size_t count,
|
||||
loff_t *offset)
|
||||
{
|
||||
int ret;
|
||||
u8 value8[MAX_FPGA_REG_SIZE];
|
||||
int i;
|
||||
|
||||
if ((count > MAX_FPGA_REG_SIZE) || ((file->f_pos + count) > MAX_FPGA_REG_SIZE)) {
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
for (i = 0; i < count; i++) {
|
||||
ret = lpc_fpga_read((int)(file->f_pos + i), &value8[i]);
|
||||
if (ret) {
|
||||
LPC_DBG_ERROR("lpc_fpga_read i %d addr 0x%x failed ret %d.\n",
|
||||
i, ((unsigned int)file->f_pos + i), ret);
|
||||
return i;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if (copy_to_user(buf, value8, count)) {
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
|
||||
static ssize_t lpc_misc_fpga_dev_write (struct file *file, const char __user *buf, size_t count,
|
||||
loff_t *offset)
|
||||
{
|
||||
int ret;
|
||||
u8 value8[MAX_FPGA_REG_SIZE];
|
||||
int i;
|
||||
|
||||
if ((count > MAX_FPGA_REG_SIZE) || ((file->f_pos + count) > MAX_FPGA_REG_SIZE)) {
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
if (copy_from_user(value8, buf, count)) {
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
for (i = 0; i < count; i++) {
|
||||
ret = lpc_fpga_write((int)(file->f_pos + i), value8[i]);
|
||||
if (ret) {
|
||||
LPC_DBG_ERROR("lpc_fpga_write i %d addr 0x%x value 0x%x failed ret %d.\n",
|
||||
i, (int)(file->f_pos + i), value8[i], ret);
|
||||
return i;
|
||||
}
|
||||
}
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
|
||||
static loff_t lpc_misc_fpga_dev_llseek(struct file *file, loff_t offset, int origin)
|
||||
{
|
||||
loff_t ret;
|
||||
|
||||
#if LINUX_VERSION_CODE < KERNEL_VERSION(4,0,36)
|
||||
mutex_lock(&file->f_path.dentry->d_inode->i_mutex);
|
||||
#else
|
||||
/* do noting add tjm */
|
||||
inode_lock(file_inode(file));
|
||||
#endif
|
||||
|
||||
switch (origin) {
|
||||
case 0:
|
||||
file->f_pos = offset;
|
||||
ret = file->f_pos;
|
||||
break;
|
||||
case 1:
|
||||
file->f_pos += offset;
|
||||
ret = file->f_pos;
|
||||
break;
|
||||
default:
|
||||
ret = -EINVAL;
|
||||
}
|
||||
|
||||
#if LINUX_VERSION_CODE < KERNEL_VERSION(4,0,36)
|
||||
mutex_unlock(&file->f_path.dentry->d_inode->i_mutex);
|
||||
#else
|
||||
/* do noting add tjm */
|
||||
inode_unlock(file_inode(file));
|
||||
#endif
|
||||
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
static long lpc_misc_fpga_dev_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
static int lpc_misc_fpga_dev_open(struct inode *inode, struct file *file)
|
||||
{
|
||||
file->private_data = NULL;
|
||||
file->f_pos = 0;
|
||||
return 0;
|
||||
|
||||
}
|
||||
|
||||
static int lpc_misc_fpga_dev_release(struct inode *inode, struct file *file)
|
||||
{
|
||||
file->private_data = NULL;
|
||||
file->f_pos = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const struct file_operations lpc_misc_fpga_dev_fops = {
|
||||
.owner = THIS_MODULE,
|
||||
.llseek = lpc_misc_fpga_dev_llseek,
|
||||
.read = lpc_misc_fpga_dev_read,
|
||||
.write = lpc_misc_fpga_dev_write,
|
||||
.unlocked_ioctl = lpc_misc_fpga_dev_ioctl,
|
||||
.open = lpc_misc_fpga_dev_open,
|
||||
.release = lpc_misc_fpga_dev_release,
|
||||
};
|
||||
|
||||
static struct miscdevice lpc_misc_cpld_dev = {
|
||||
.minor = MISC_DYNAMIC_MINOR,
|
||||
.name = "lpc_cpld",
|
||||
.fops = &lpc_misc_cpld_dev_fops,
|
||||
};
|
||||
|
||||
static struct miscdevice lpc_misc_fpga_dev = {
|
||||
.minor = MISC_DYNAMIC_MINOR,
|
||||
.name = "lpc_fpga",
|
||||
.fops = &lpc_misc_fpga_dev_fops,
|
||||
};
|
||||
|
||||
static int lpc_misc_drv_init(void)
|
||||
{
|
||||
if (misc_register(&lpc_misc_cpld_dev) != 0) {
|
||||
LPC_DBG_ERROR("Register %s failed.\r\n", lpc_misc_cpld_dev.name);
|
||||
return -ENXIO;
|
||||
}
|
||||
|
||||
if (misc_register(&lpc_misc_fpga_dev) != 0) {
|
||||
LPC_DBG_ERROR("Register %s failed.\r\n", lpc_misc_fpga_dev.name);
|
||||
return -ENXIO;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void lpc_misc_drv_exit(void)
|
||||
{
|
||||
misc_deregister(&lpc_misc_cpld_dev);
|
||||
misc_deregister(&lpc_misc_fpga_dev);
|
||||
}
|
||||
|
||||
#define LPC_MAKE_PCI_IO_RANGE(__base) ((0xfc0001) | ((__base) & (0xFFFC)))
|
||||
|
||||
static int lpc_pci_cfg_init(struct pci_dev *pdev,
|
||||
const struct pci_device_id *id)
|
||||
{
|
||||
int i;
|
||||
int size;
|
||||
|
||||
size = ARRAY_SIZE(g_rg_lpc_dev_default);
|
||||
|
||||
for (i = 0; i < size; i++) {
|
||||
pci_write_config_dword(pdev, g_rg_lpc_dev[i].lpc_pci_addr, LPC_MAKE_PCI_IO_RANGE(g_rg_lpc_dev[i].base));
|
||||
LPC_DBG_VERBOSE("set lpc pci cfg[addr: 0x%x, value:0x%x].\n", LPC_PCI_CFG_BASE(i), LPC_MAKE_PCI_IO_RANGE(g_rg_lpc_dev[i].base));
|
||||
if (!request_region(g_rg_lpc_dev[i].base, g_rg_lpc_dev[i].size, "rg_lpc")) {
|
||||
LPC_DBG_ERROR("request_region [0x%x][0x%x] failed!\n", g_rg_lpc_dev[i].base, g_rg_lpc_dev[i].size);
|
||||
return -EBUSY;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void lpc_pci_cfg_exit(void)
|
||||
{
|
||||
int i;
|
||||
int size;
|
||||
|
||||
size = ARRAY_SIZE(g_rg_lpc_dev_default);
|
||||
for (i = 0; i < size; i++) {
|
||||
release_region(g_rg_lpc_dev[i].base, g_rg_lpc_dev[i].size);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
static int rg_lpc_cpld_probe(struct pci_dev *pdev,
|
||||
const struct pci_device_id *id)
|
||||
{
|
||||
int ret;
|
||||
|
||||
LPC_DBG_VERBOSE("Enter.\n");
|
||||
ret = lpc_pci_cfg_init(pdev, id);
|
||||
if (ret) {
|
||||
LPC_DBG_ERROR("lpc_pci_cfg_init failed ret %d.\n", ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
ret = lpc_misc_drv_init();
|
||||
if (ret) {
|
||||
LPC_DBG_ERROR("lpc_misc_drv_init failed ret %d.\n", ret);
|
||||
return ret;
|
||||
}
|
||||
LPC_DBG_VERBOSE("Leave success\n");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void rg_lpc_cpld_remove(struct pci_dev *pdev)
|
||||
{
|
||||
LPC_DBG_VERBOSE("Enter.\n");
|
||||
lpc_misc_drv_exit();
|
||||
lpc_pci_cfg_exit();
|
||||
LPC_DBG_VERBOSE("Leave.\n");
|
||||
}
|
||||
|
||||
|
||||
#define PCI_VENDOR_ID_D1527_LPC (0x8c54)
|
||||
#define PCI_VENDOR_ID_C3000_LPC (0x19dc)
|
||||
|
||||
#if 0
|
||||
static const struct pci_device_id rg_lpc_cpld_pcidev_id[] = {
|
||||
{ PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_VENDOR_ID_C3000_LPC) },
|
||||
{ PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_VENDOR_ID_D1527_LPC) },
|
||||
{ 0, }
|
||||
};
|
||||
MODULE_DEVICE_TABLE(pci, rg_lpc_cpld_pcidev_id);
|
||||
|
||||
static struct pci_driver rg_lpc_driver = {
|
||||
.name = "rg_lpc",
|
||||
.id_table = rg_lpc_cpld_pcidev_id,
|
||||
.probe = rg_lpc_cpld_probe,
|
||||
.remove = rg_lpc_cpld_remove,
|
||||
};
|
||||
|
||||
module_pci_driver(rg_lpc_driver);
|
||||
#else
|
||||
static int __init lpc_dbg_init(void)
|
||||
{
|
||||
struct pci_dev *pdev = NULL;
|
||||
int ret;
|
||||
|
||||
LPC_DBG_VERBOSE("Enter.\n");
|
||||
|
||||
pdev = pci_get_device(PCI_VENDOR_ID_INTEL, PCI_VENDOR_ID_D1527_LPC, pdev);
|
||||
if (!pdev) {
|
||||
LPC_DBG_ERROR("pci_get_device(0x8086, 0x8c54) failed!\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
ret = rg_lpc_cpld_probe(pdev, NULL);
|
||||
LPC_DBG_VERBOSE("Leave ret %d.\n", ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void __exit lpc_dbg_exit(void)
|
||||
{
|
||||
LPC_DBG_VERBOSE("Enter.\n");
|
||||
rg_lpc_cpld_remove(NULL);
|
||||
LPC_DBG_VERBOSE("Leave.\n");
|
||||
}
|
||||
|
||||
|
||||
|
||||
module_init(lpc_dbg_init);
|
||||
module_exit(lpc_dbg_exit);
|
||||
|
||||
#endif
|
||||
MODULE_LICENSE("GPL");
|
||||
MODULE_AUTHOR("support <support@ragile.com>");
|
||||
|
39
platform/broadcom/sonic-platform-modules-ragile/common/modules/lpc_dbg.h
Executable file
39
platform/broadcom/sonic-platform-modules-ragile/common/modules/lpc_dbg.h
Executable file
@ -0,0 +1,39 @@
|
||||
#ifndef __ETH_CMD_TYPES_H__
|
||||
#define __ETH_CMD_TYPES_H__
|
||||
|
||||
typedef enum {
|
||||
ETH_START = 1,
|
||||
ETH_SHOW,
|
||||
ETH_SET,
|
||||
ETH_TEST,
|
||||
ETH_MAC_REG,
|
||||
ETH_PHY_REG,
|
||||
} ether_dbg_top_cmd_t;
|
||||
|
||||
typedef enum {
|
||||
ETH_MAC_REG_READ = 1,
|
||||
ETH_MAC_REG_WRITE,
|
||||
ETH_MAC_REG_CHECK,
|
||||
ETH_MAC_REG_DUMP_ALL,
|
||||
ETH_MAC_REG_DUMP_PCI_CFG_ALL,
|
||||
} ether_mac_reg_cmd_t;
|
||||
|
||||
|
||||
#define ETH_DBG_TYPE(cmd1, cmd2, cmd3, cmd4) \
|
||||
((cmd1) | ((cmd2) << 8) | ((cmd3) << 16) | ((cmd4) << 24))
|
||||
#define ETH_DBG_PARSE_TYPE(type, cmd1, cmd2, cmd3, cmd4) \
|
||||
do {\
|
||||
(cmd1) = (type) & 0xff;\
|
||||
(cmd2) = ((type) >> 8) & 0xff;\
|
||||
(cmd3) = ((type) >> 16) & 0xff;\
|
||||
(cmd4) = ((type) >> 24) & 0xff;\
|
||||
} while (0)
|
||||
|
||||
typedef struct {
|
||||
int type;
|
||||
int length;
|
||||
unsigned char value[128];
|
||||
} ether_msg_t;
|
||||
|
||||
|
||||
#endif /* __ETH_CMD_TYPES_H__ */
|
@ -130,26 +130,26 @@ enum pmbus_regs {
|
||||
PMBUS_MFR_DATE = 0x9D,
|
||||
PMBUS_MFR_SERIAL = 0x9E,
|
||||
|
||||
/*
|
||||
* Virtual registers.
|
||||
* Useful to support attributes which are not supported by standard PMBus
|
||||
* registers but exist as manufacturer specific registers on individual chips.
|
||||
* Must be mapped to real registers in device specific code.
|
||||
*
|
||||
* Semantics:
|
||||
* Virtual registers are all word size.
|
||||
* READ registers are read-only; writes are either ignored or return an error.
|
||||
* RESET registers are read/write. Reading reset registers returns zero
|
||||
* (used for detection), writing any value causes the associated history to be
|
||||
* reset.
|
||||
* Virtual registers have to be handled in device specific driver code. Chip
|
||||
* driver code returns non-negative register values if a virtual register is
|
||||
* supported, or a negative error code if not. The chip driver may return
|
||||
* -ENODATA or any other error code in this case, though an error code other
|
||||
* than -ENODATA is handled more efficiently and thus preferred. Either case,
|
||||
* the calling PMBus core code will abort if the chip driver returns an error
|
||||
* code when reading or writing virtual registers.
|
||||
*/
|
||||
/*
|
||||
* Virtual registers.
|
||||
* Useful to support attributes which are not supported by standard PMBus
|
||||
* registers but exist as manufacturer specific registers on individual chips.
|
||||
* Must be mapped to real registers in device specific code.
|
||||
*
|
||||
* Semantics:
|
||||
* Virtual registers are all word size.
|
||||
* READ registers are read-only; writes are either ignored or return an error.
|
||||
* RESET registers are read/write. Reading reset registers returns zero
|
||||
* (used for detection), writing any value causes the associated history to be
|
||||
* reset.
|
||||
* Virtual registers have to be handled in device specific driver code. Chip
|
||||
* driver code returns non-negative register values if a virtual register is
|
||||
* supported, or a negative error code if not. The chip driver may return
|
||||
* -ENODATA or any other error code in this case, though an error code other
|
||||
* than -ENODATA is handled more efficiently and thus preferred. Either case,
|
||||
* the calling PMBus core code will abort if the chip driver returns an error
|
||||
* code when reading or writing virtual registers.
|
||||
*/
|
||||
PMBUS_VIRT_BASE = 0x100,
|
||||
PMBUS_VIRT_READ_TEMP_AVG,
|
||||
PMBUS_VIRT_READ_TEMP_MIN,
|
||||
@ -190,6 +190,33 @@ enum pmbus_regs {
|
||||
PMBUS_VIRT_VMON_UV_FAULT_LIMIT,
|
||||
PMBUS_VIRT_VMON_OV_FAULT_LIMIT,
|
||||
PMBUS_VIRT_STATUS_VMON,
|
||||
|
||||
/*
|
||||
* RPM and PWM Fan control
|
||||
*
|
||||
* Drivers wanting to expose PWM control must define the behaviour of
|
||||
* PMBUS_VIRT_PWM_[1-4] and PMBUS_VIRT_PWM_ENABLE_[1-4] in the
|
||||
* {read,write}_word_data callback.
|
||||
*
|
||||
* pmbus core provides a default implementation for
|
||||
* PMBUS_VIRT_FAN_TARGET_[1-4].
|
||||
*
|
||||
* TARGET, PWM and PWM_ENABLE members must be defined sequentially;
|
||||
* pmbus core uses the difference between the provided register and
|
||||
* it's _1 counterpart to calculate the FAN/PWM ID.
|
||||
*/
|
||||
PMBUS_VIRT_FAN_TARGET_1,
|
||||
PMBUS_VIRT_FAN_TARGET_2,
|
||||
PMBUS_VIRT_FAN_TARGET_3,
|
||||
PMBUS_VIRT_FAN_TARGET_4,
|
||||
PMBUS_VIRT_PWM_1,
|
||||
PMBUS_VIRT_PWM_2,
|
||||
PMBUS_VIRT_PWM_3,
|
||||
PMBUS_VIRT_PWM_4,
|
||||
PMBUS_VIRT_PWM_ENABLE_1,
|
||||
PMBUS_VIRT_PWM_ENABLE_2,
|
||||
PMBUS_VIRT_PWM_ENABLE_3,
|
||||
PMBUS_VIRT_PWM_ENABLE_4,
|
||||
};
|
||||
|
||||
/*
|
||||
@ -223,6 +250,8 @@ enum pmbus_regs {
|
||||
#define PB_FAN_1_RPM BIT(6)
|
||||
#define PB_FAN_1_INSTALLED BIT(7)
|
||||
|
||||
enum pmbus_fan_mode { percent = 0, rpm };
|
||||
|
||||
/*
|
||||
* STATUS_BYTE, STATUS_WORD (lower)
|
||||
*/
|
||||
@ -313,6 +342,7 @@ enum pmbus_sensor_classes {
|
||||
PSC_POWER,
|
||||
PSC_TEMPERATURE,
|
||||
PSC_FAN,
|
||||
PSC_PWM,
|
||||
PSC_NUM_CLASSES /* Number of power sensor classes */
|
||||
};
|
||||
|
||||
@ -339,6 +369,10 @@ enum pmbus_sensor_classes {
|
||||
#define PMBUS_HAVE_STATUS_FAN34 BIT(17)
|
||||
#define PMBUS_HAVE_VMON BIT(18)
|
||||
#define PMBUS_HAVE_STATUS_VMON BIT(19)
|
||||
#define PMBUS_HAVE_PWM12 BIT(20)
|
||||
#define PMBUS_HAVE_PWM34 BIT(21)
|
||||
|
||||
#define PMBUS_PAGE_VIRTUAL BIT(31)
|
||||
|
||||
enum pmbus_data_format { linear = 0, direct, vid };
|
||||
enum vrm_version { vr11 = 0, vr12, vr13 };
|
||||
@ -370,7 +404,7 @@ struct pmbus_driver_info {
|
||||
int (*read_byte_data)(struct i2c_client *client, int page, int reg);
|
||||
int (*read_word_data)(struct i2c_client *client, int page, int reg);
|
||||
int (*write_word_data)(struct i2c_client *client, int page, int reg,
|
||||
u16 word);
|
||||
u16 word);
|
||||
int (*write_byte)(struct i2c_client *client, int page, u8 value);
|
||||
/*
|
||||
* The identify function determines supported PMBus functionality.
|
||||
@ -404,21 +438,29 @@ extern const struct regulator_ops pmbus_regulator_ops;
|
||||
/* Function declarations */
|
||||
|
||||
void pmbus_clear_cache(struct i2c_client *client);
|
||||
int pmbus_set_page(struct i2c_client *client, u8 page);
|
||||
int pmbus_read_word_data(struct i2c_client *client, u8 page, u8 reg);
|
||||
int pmbus_write_word_data(struct i2c_client *client, u8 page, u8 reg, u16 word);
|
||||
int pmbus_set_page(struct i2c_client *client, int page);
|
||||
int pmbus_read_word_data(struct i2c_client *client, int page, u8 reg);
|
||||
int pmbus_write_word_data(struct i2c_client *client, int page, u8 reg, u16 word);
|
||||
int pmbus_read_byte_data(struct i2c_client *client, int page, u8 reg);
|
||||
int pmbus_write_byte(struct i2c_client *client, int page, u8 value);
|
||||
int pmbus_write_byte_data(struct i2c_client *client, int page, u8 reg,
|
||||
u8 value);
|
||||
u8 value);
|
||||
int pmbus_update_byte_data(struct i2c_client *client, int page, u8 reg,
|
||||
u8 mask, u8 value);
|
||||
u8 mask, u8 value);
|
||||
void pmbus_clear_faults(struct i2c_client *client);
|
||||
bool pmbus_check_byte_register(struct i2c_client *client, int page, int reg);
|
||||
bool pmbus_check_word_register(struct i2c_client *client, int page, int reg);
|
||||
int pmbus_do_probe(struct i2c_client *client, const struct i2c_device_id *id,
|
||||
struct pmbus_driver_info *info);
|
||||
struct pmbus_driver_info *info);
|
||||
int pmbus_do_remove(struct i2c_client *client);
|
||||
const struct pmbus_driver_info *pmbus_get_driver_info(struct i2c_client
|
||||
*client);
|
||||
*client);
|
||||
int pmbus_get_fan_rate_device(struct i2c_client *client, int page, int id,
|
||||
enum pmbus_fan_mode mode);
|
||||
int pmbus_get_fan_rate_cached(struct i2c_client *client, int page, int id,
|
||||
enum pmbus_fan_mode mode);
|
||||
int pmbus_update_fan(struct i2c_client *client, int page, int id,
|
||||
u8 config, u8 mask, u16 command);
|
||||
struct dentry *pmbus_get_debugfs_dir(struct i2c_client *client);
|
||||
|
||||
#endif /* PMBUS_H */
|
||||
|
@ -0,0 +1,79 @@
|
||||
#include <linux/module.h>
|
||||
#include <linux/kernel.h>
|
||||
#include <linux/sysfs.h>
|
||||
#include <linux/slab.h>
|
||||
#include <linux/stat.h>
|
||||
#include <linux/uaccess.h>
|
||||
#include <linux/init.h>
|
||||
#include <linux/fs.h>
|
||||
#include <linux/i2c.h>
|
||||
#include <linux/i2c-mux.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/delay.h>
|
||||
#include <linux/i2c-smbus.h>
|
||||
#include <linux/string.h>
|
||||
|
||||
static int dfd_my_type = 0;
|
||||
module_param(dfd_my_type, int, S_IRUGO | S_IWUSR);
|
||||
|
||||
int g_common_debug_error = 0;
|
||||
module_param(g_common_debug_error, int, S_IRUGO | S_IWUSR);
|
||||
|
||||
int g_common_debug_verbose = 0;
|
||||
module_param(g_common_debug_verbose, int, S_IRUGO | S_IWUSR);
|
||||
|
||||
#define RAGILE_COMMON_DEBUG_VERBOSE(fmt, args...) do { \
|
||||
if (g_common_debug_verbose) { \
|
||||
printk(KERN_ERR "[RAGILE_COMMON][VER][func:%s line:%d]\r\n"fmt, __func__, __LINE__, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define RAGILE_COMMON_DEBUG_ERROR(fmt, args...) do { \
|
||||
if (g_common_debug_error) { \
|
||||
printk(KERN_ERR "[RAGILE_COMMON][ERROR][func:%s line:%d]\r\n"fmt, __func__, __LINE__, ## args); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
|
||||
int dfd_get_my_card_type(void)
|
||||
{
|
||||
int type;
|
||||
int cnt;
|
||||
|
||||
if (dfd_my_type != 0) {
|
||||
RAGILE_COMMON_DEBUG_VERBOSE("my_type = 0x%x\r\n", dfd_my_type);
|
||||
return dfd_my_type;
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
EXPORT_SYMBOL(dfd_get_my_card_type);
|
||||
|
||||
static int __init ragile_common_init(void)
|
||||
{
|
||||
int ret;
|
||||
|
||||
RAGILE_COMMON_DEBUG_VERBOSE("Enter.\n");
|
||||
ret = dfd_get_my_card_type();
|
||||
if (ret <= 0) {
|
||||
RAGILE_COMMON_DEBUG_ERROR("dfd_get_my_card_type failed, ret %d.\n", ret);
|
||||
printk(KERN_ERR "Warning: Device type get failed, please check the TLV-EEPROM!\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
RAGILE_COMMON_DEBUG_VERBOSE("Leave success type 0x%x.\n", ret);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void __exit ragile_common_exit(void)
|
||||
{
|
||||
RAGILE_COMMON_DEBUG_VERBOSE("Exit.\n");
|
||||
}
|
||||
|
||||
module_init(ragile_common_init);
|
||||
module_exit(ragile_common_exit);
|
||||
|
||||
MODULE_DESCRIPTION("ragile Platform Support");
|
||||
MODULE_AUTHOR("support <support@ragile.com>");
|
||||
MODULE_LICENSE("GPL");
|
||||
|
@ -62,11 +62,11 @@ static DEFINE_SPINLOCK(sio_lock);
|
||||
/****************** i2c adapter with gpio ***********************/
|
||||
|
||||
static struct i2c_gpio_platform_data i2c_pdata = {
|
||||
.timeout = 200,
|
||||
.udelay = 10,
|
||||
.scl_is_output_only = 0,
|
||||
.sda_is_open_drain = 0,
|
||||
.scl_is_open_drain = 0,
|
||||
.timeout = 200,
|
||||
.udelay = 10,
|
||||
.scl_is_output_only = 0,
|
||||
.sda_is_open_drain = 0,
|
||||
.scl_is_open_drain = 0,
|
||||
};
|
||||
|
||||
static struct gpiod_lookup_table rg_gpio_lookup_table = {
|
||||
@ -81,272 +81,272 @@ static struct gpiod_lookup_table rg_gpio_lookup_table = {
|
||||
|
||||
static void i2c_gpio_release(struct device *dev)
|
||||
{
|
||||
return;
|
||||
return;
|
||||
}
|
||||
|
||||
static struct platform_device i2c_gpio = {
|
||||
.name = "i2c-gpio",
|
||||
.num_resources = 0,
|
||||
.id = -1,
|
||||
.name = "i2c-gpio",
|
||||
.num_resources = 0,
|
||||
.id = -1,
|
||||
|
||||
.dev = {
|
||||
.platform_data = &i2c_pdata,
|
||||
.release = i2c_gpio_release,
|
||||
}
|
||||
.dev = {
|
||||
.platform_data = &i2c_pdata,
|
||||
.release = i2c_gpio_release,
|
||||
}
|
||||
};
|
||||
|
||||
static int xeon_gpio_get(struct gpio_chip *gc, unsigned gpio_num)
|
||||
{
|
||||
unsigned int data;
|
||||
unsigned int bank, offset;
|
||||
unsigned long flags;
|
||||
unsigned int data;
|
||||
unsigned int bank, offset;
|
||||
unsigned long flags;
|
||||
|
||||
data = 0;
|
||||
bank = gpio_num / BANKSIZE;
|
||||
offset = gpio_num % BANKSIZE;
|
||||
bank = gpio_num / BANKSIZE;
|
||||
offset = gpio_num % BANKSIZE;
|
||||
|
||||
GPIO_XEON_SPIN_LOCK(sio_lock, flags);
|
||||
if (bank == 0) {
|
||||
data = inl(GP_LVL) & (1 << offset);
|
||||
if (data) {
|
||||
data = 1;
|
||||
}
|
||||
} else if (bank == 1) {
|
||||
data = inl(GP_LVL2) & (1 << offset);
|
||||
if (data) {
|
||||
data = 1;
|
||||
}
|
||||
} else if (bank == 2) {
|
||||
data = inl(GP_LVL3) & (1 << offset);
|
||||
if (data) {
|
||||
data = 1;
|
||||
}
|
||||
}
|
||||
GPIO_XEON_SPIN_UNLOCK(sio_lock, flags);
|
||||
GPIO_XEON_SPIN_LOCK(sio_lock, flags);
|
||||
if (bank == 0) {
|
||||
data = inl(GP_LVL) & (1 << offset);
|
||||
if (data) {
|
||||
data = 1;
|
||||
}
|
||||
} else if (bank == 1) {
|
||||
data = inl(GP_LVL2) & (1 << offset);
|
||||
if (data) {
|
||||
data = 1;
|
||||
}
|
||||
} else if (bank == 2) {
|
||||
data = inl(GP_LVL3) & (1 << offset);
|
||||
if (data) {
|
||||
data = 1;
|
||||
}
|
||||
}
|
||||
GPIO_XEON_SPIN_UNLOCK(sio_lock, flags);
|
||||
|
||||
return data;
|
||||
return data;
|
||||
}
|
||||
|
||||
static int xeon_gpio_direction_in(struct gpio_chip *gc, unsigned gpio_num)
|
||||
{
|
||||
unsigned int data;
|
||||
unsigned int bank, offset;
|
||||
unsigned long flags;
|
||||
unsigned int data;
|
||||
unsigned int bank, offset;
|
||||
unsigned long flags;
|
||||
|
||||
bank = gpio_num / BANKSIZE;
|
||||
offset = gpio_num % BANKSIZE;
|
||||
bank = gpio_num / BANKSIZE;
|
||||
offset = gpio_num % BANKSIZE;
|
||||
|
||||
GPIO_XEON_SPIN_LOCK(sio_lock, flags);
|
||||
if (bank == 0) {
|
||||
data = inl(GP_IO_SEL);
|
||||
data = data | (1 << offset);
|
||||
outl(data, GP_IO_SEL);
|
||||
} else if (bank == 1) {
|
||||
data = inl(GP_IO_SEL2);
|
||||
data = data | (1 << offset);
|
||||
outl(data, GP_IO_SEL2);
|
||||
} else if (bank == 2) {
|
||||
data = inl(GP_IO_SEL3);
|
||||
data = data | (1 << offset);
|
||||
outl(data, GP_IO_SEL3);
|
||||
}
|
||||
GPIO_XEON_SPIN_UNLOCK(sio_lock, flags);
|
||||
GPIO_XEON_SPIN_LOCK(sio_lock, flags);
|
||||
if (bank == 0) {
|
||||
data = inl(GP_IO_SEL);
|
||||
data = data | (1 << offset);
|
||||
outl(data, GP_IO_SEL);
|
||||
} else if (bank == 1) {
|
||||
data = inl(GP_IO_SEL2);
|
||||
data = data | (1 << offset);
|
||||
outl(data, GP_IO_SEL2);
|
||||
} else if (bank == 2) {
|
||||
data = inl(GP_IO_SEL3);
|
||||
data = data | (1 << offset);
|
||||
outl(data, GP_IO_SEL3);
|
||||
}
|
||||
GPIO_XEON_SPIN_UNLOCK(sio_lock, flags);
|
||||
|
||||
return 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void xeon_gpio_set(struct gpio_chip *gc,
|
||||
unsigned gpio_num, int val)
|
||||
unsigned gpio_num, int val)
|
||||
{
|
||||
unsigned int data;
|
||||
unsigned int bank, offset;
|
||||
unsigned long flags;
|
||||
unsigned int data;
|
||||
unsigned int bank, offset;
|
||||
unsigned long flags;
|
||||
|
||||
bank = gpio_num / BANKSIZE;
|
||||
offset = gpio_num % BANKSIZE;
|
||||
bank = gpio_num / BANKSIZE;
|
||||
offset = gpio_num % BANKSIZE;
|
||||
|
||||
GPIO_XEON_SPIN_LOCK(sio_lock, flags);
|
||||
if (bank == 0) {
|
||||
data = inl(GP_LVL);
|
||||
if (val) {
|
||||
data = data | (1 << offset);
|
||||
} else {
|
||||
data = data & ~(1 << offset);
|
||||
}
|
||||
outl(data, GP_LVL);
|
||||
} else if (bank == 1) {
|
||||
data = inl(GP_LVL2);
|
||||
if (val) {
|
||||
data = data | (1 << offset);
|
||||
} else {
|
||||
data = data & ~(1 << offset);
|
||||
}
|
||||
outl(data, GP_LVL2);
|
||||
} else if (bank == 2) {
|
||||
data = inl(GP_LVL3);
|
||||
if (val) {
|
||||
data = data | (1 << offset);
|
||||
} else {
|
||||
data = data & ~(1 << offset);
|
||||
}
|
||||
outl(data, GP_LVL3);
|
||||
}
|
||||
GPIO_XEON_SPIN_UNLOCK(sio_lock, flags);
|
||||
GPIO_XEON_SPIN_LOCK(sio_lock, flags);
|
||||
if (bank == 0) {
|
||||
data = inl(GP_LVL);
|
||||
if (val) {
|
||||
data = data | (1 << offset);
|
||||
} else {
|
||||
data = data & ~(1 << offset);
|
||||
}
|
||||
outl(data, GP_LVL);
|
||||
} else if (bank == 1) {
|
||||
data = inl(GP_LVL2);
|
||||
if (val) {
|
||||
data = data | (1 << offset);
|
||||
} else {
|
||||
data = data & ~(1 << offset);
|
||||
}
|
||||
outl(data, GP_LVL2);
|
||||
} else if (bank == 2) {
|
||||
data = inl(GP_LVL3);
|
||||
if (val) {
|
||||
data = data | (1 << offset);
|
||||
} else {
|
||||
data = data & ~(1 << offset);
|
||||
}
|
||||
outl(data, GP_LVL3);
|
||||
}
|
||||
GPIO_XEON_SPIN_UNLOCK(sio_lock, flags);
|
||||
}
|
||||
|
||||
static int xeon_gpio_direction_out(struct gpio_chip *gc,
|
||||
unsigned gpio_num, int val)
|
||||
unsigned gpio_num, int val)
|
||||
{
|
||||
unsigned int data;
|
||||
unsigned int bank, offset;
|
||||
unsigned long flags;
|
||||
unsigned int data;
|
||||
unsigned int bank, offset;
|
||||
unsigned long flags;
|
||||
|
||||
bank = gpio_num / BANKSIZE;
|
||||
offset = gpio_num % BANKSIZE;
|
||||
bank = gpio_num / BANKSIZE;
|
||||
offset = gpio_num % BANKSIZE;
|
||||
|
||||
GPIO_XEON_SPIN_LOCK(sio_lock, flags);
|
||||
if (bank == 0) {
|
||||
data = inl(GP_IO_SEL);
|
||||
data = data & ~(1 << offset);
|
||||
outl(data, GP_IO_SEL);
|
||||
GPIO_XEON_SPIN_LOCK(sio_lock, flags);
|
||||
if (bank == 0) {
|
||||
data = inl(GP_IO_SEL);
|
||||
data = data & ~(1 << offset);
|
||||
outl(data, GP_IO_SEL);
|
||||
|
||||
data = inl(GP_LVL);
|
||||
if (val) {
|
||||
data = data | (1 << offset);
|
||||
} else {
|
||||
data = data & ~(1 << offset);
|
||||
}
|
||||
outl(data, GP_LVL);
|
||||
} else if (bank == 1) {
|
||||
data = inl(GP_IO_SEL2);
|
||||
data = data & ~(1 << offset);
|
||||
outl(data, GP_IO_SEL2);
|
||||
data = inl(GP_LVL);
|
||||
if (val) {
|
||||
data = data | (1 << offset);
|
||||
} else {
|
||||
data = data & ~(1 << offset);
|
||||
}
|
||||
outl(data, GP_LVL);
|
||||
} else if (bank == 1) {
|
||||
data = inl(GP_IO_SEL2);
|
||||
data = data & ~(1 << offset);
|
||||
outl(data, GP_IO_SEL2);
|
||||
|
||||
data = inl(GP_LVL2);
|
||||
if (val) {
|
||||
data = data | (1 << offset);
|
||||
} else {
|
||||
data = data & ~(1 << offset);
|
||||
}
|
||||
outl(data, GP_LVL2);
|
||||
} else if (bank == 2) {
|
||||
data = inl(GP_IO_SEL3);
|
||||
data = data & ~(1 << offset);
|
||||
outl(data, GP_IO_SEL3);
|
||||
data = inl(GP_LVL2);
|
||||
if (val) {
|
||||
data = data | (1 << offset);
|
||||
} else {
|
||||
data = data & ~(1 << offset);
|
||||
}
|
||||
outl(data, GP_LVL2);
|
||||
} else if (bank == 2) {
|
||||
data = inl(GP_IO_SEL3);
|
||||
data = data & ~(1 << offset);
|
||||
outl(data, GP_IO_SEL3);
|
||||
|
||||
data = inl(GP_LVL3);
|
||||
if (val) {
|
||||
data = data | (1 << offset);
|
||||
} else {
|
||||
data = data & ~(1 << offset);
|
||||
}
|
||||
outl(data, GP_LVL3);
|
||||
}
|
||||
GPIO_XEON_SPIN_UNLOCK(sio_lock, flags);
|
||||
data = inl(GP_LVL3);
|
||||
if (val) {
|
||||
data = data | (1 << offset);
|
||||
} else {
|
||||
data = data & ~(1 << offset);
|
||||
}
|
||||
outl(data, GP_LVL3);
|
||||
}
|
||||
GPIO_XEON_SPIN_UNLOCK(sio_lock, flags);
|
||||
|
||||
return 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int xeon_gpio_request(struct gpio_chip *chip, unsigned int offset)
|
||||
{
|
||||
unsigned int data;
|
||||
unsigned int bank, tmp_offset;
|
||||
unsigned long flags;
|
||||
unsigned int data;
|
||||
unsigned int bank, tmp_offset;
|
||||
unsigned long flags;
|
||||
|
||||
bank = offset / BANKSIZE;
|
||||
tmp_offset = offset % BANKSIZE;
|
||||
bank = offset / BANKSIZE;
|
||||
tmp_offset = offset % BANKSIZE;
|
||||
|
||||
GPIO_XEON_SPIN_LOCK(sio_lock, flags);
|
||||
if (bank == 0) {
|
||||
data = inl(GPIO_USE_SEL);
|
||||
data = data | (1 << tmp_offset);
|
||||
outl(data, GPIO_USE_SEL);
|
||||
} else if (bank == 1) {
|
||||
data = inl(GPIO_USE_SEL2);
|
||||
data = data | (1 << tmp_offset);
|
||||
outl(data, GPIO_USE_SEL2);
|
||||
} else if (bank == 2) {
|
||||
data = inl(GPIO_USE_SEL3);
|
||||
data = data | (1 << tmp_offset);
|
||||
outl(data, GPIO_USE_SEL3);
|
||||
}
|
||||
GPIO_XEON_SPIN_UNLOCK(sio_lock, flags);
|
||||
return 0;
|
||||
GPIO_XEON_SPIN_LOCK(sio_lock, flags);
|
||||
if (bank == 0) {
|
||||
data = inl(GPIO_USE_SEL);
|
||||
data = data | (1 << tmp_offset);
|
||||
outl(data, GPIO_USE_SEL);
|
||||
} else if (bank == 1) {
|
||||
data = inl(GPIO_USE_SEL2);
|
||||
data = data | (1 << tmp_offset);
|
||||
outl(data, GPIO_USE_SEL2);
|
||||
} else if (bank == 2) {
|
||||
data = inl(GPIO_USE_SEL3);
|
||||
data = data | (1 << tmp_offset);
|
||||
outl(data, GPIO_USE_SEL3);
|
||||
}
|
||||
GPIO_XEON_SPIN_UNLOCK(sio_lock, flags);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void xeon_gpio_free(struct gpio_chip *chip, unsigned int offset)
|
||||
{
|
||||
unsigned int data;
|
||||
unsigned int bank, tmp_offset;
|
||||
unsigned long flags;
|
||||
unsigned int data;
|
||||
unsigned int bank, tmp_offset;
|
||||
unsigned long flags;
|
||||
|
||||
bank = offset / BANKSIZE;
|
||||
tmp_offset = offset % BANKSIZE;
|
||||
bank = offset / BANKSIZE;
|
||||
tmp_offset = offset % BANKSIZE;
|
||||
|
||||
GPIO_XEON_SPIN_LOCK(sio_lock, flags);
|
||||
if (bank == 0) {
|
||||
data = inl(GPIO_USE_SEL);
|
||||
data = data & ~(1 << tmp_offset);
|
||||
outl(data, GPIO_USE_SEL);
|
||||
} else if (bank == 1) {
|
||||
data = inl(GPIO_USE_SEL2);
|
||||
data = data & ~(1 << tmp_offset);
|
||||
outl(data, GPIO_USE_SEL2);
|
||||
} else if (bank == 2) {
|
||||
data = inl(GPIO_USE_SEL3);
|
||||
data = data & ~(1 << tmp_offset);
|
||||
outl(data, GPIO_USE_SEL3);
|
||||
}
|
||||
GPIO_XEON_SPIN_UNLOCK(sio_lock, flags);
|
||||
GPIO_XEON_SPIN_LOCK(sio_lock, flags);
|
||||
if (bank == 0) {
|
||||
data = inl(GPIO_USE_SEL);
|
||||
data = data & ~(1 << tmp_offset);
|
||||
outl(data, GPIO_USE_SEL);
|
||||
} else if (bank == 1) {
|
||||
data = inl(GPIO_USE_SEL2);
|
||||
data = data & ~(1 << tmp_offset);
|
||||
outl(data, GPIO_USE_SEL2);
|
||||
} else if (bank == 2) {
|
||||
data = inl(GPIO_USE_SEL3);
|
||||
data = data & ~(1 << tmp_offset);
|
||||
outl(data, GPIO_USE_SEL3);
|
||||
}
|
||||
GPIO_XEON_SPIN_UNLOCK(sio_lock, flags);
|
||||
}
|
||||
|
||||
static struct gpio_chip xeon_gpio_chip = {
|
||||
.label = GPIO_NAME,
|
||||
.owner = THIS_MODULE,
|
||||
.get = xeon_gpio_get,
|
||||
.direction_input = xeon_gpio_direction_in,
|
||||
.set = xeon_gpio_set,
|
||||
.direction_output = xeon_gpio_direction_out,
|
||||
.request = xeon_gpio_request,
|
||||
.free = xeon_gpio_free,
|
||||
.label = GPIO_NAME,
|
||||
.owner = THIS_MODULE,
|
||||
.get = xeon_gpio_get,
|
||||
.direction_input = xeon_gpio_direction_in,
|
||||
.set = xeon_gpio_set,
|
||||
.direction_output = xeon_gpio_direction_out,
|
||||
.request = xeon_gpio_request,
|
||||
.free = xeon_gpio_free,
|
||||
};
|
||||
|
||||
static int __init xeon_gpio_init(void)
|
||||
{
|
||||
int err;
|
||||
if (!request_region(GPIO_BASE, GPIO_IOSIZE, GPIO_NAME))
|
||||
return -EBUSY;
|
||||
int err;
|
||||
if (!request_region(GPIO_BASE, GPIO_IOSIZE, GPIO_NAME))
|
||||
return -EBUSY;
|
||||
|
||||
xeon_gpio_chip.base = GPIO_BASE_ID;
|
||||
xeon_gpio_chip.ngpio = 96;
|
||||
xeon_gpio_chip.base = GPIO_BASE_ID;
|
||||
xeon_gpio_chip.ngpio = 96;
|
||||
|
||||
err = gpiochip_add_data(&xeon_gpio_chip, NULL);
|
||||
if (err < 0)
|
||||
goto gpiochip_add_err;
|
||||
gpiod_add_lookup_table(&rg_gpio_lookup_table);
|
||||
err = platform_device_register(&i2c_gpio);
|
||||
if (err < 0) {
|
||||
goto i2c_get_adapter_err;
|
||||
}
|
||||
return 0;
|
||||
err = gpiochip_add_data(&xeon_gpio_chip, NULL);
|
||||
if (err < 0)
|
||||
goto gpiochip_add_err;
|
||||
gpiod_add_lookup_table(&rg_gpio_lookup_table);
|
||||
err = platform_device_register(&i2c_gpio);
|
||||
if (err < 0) {
|
||||
goto i2c_get_adapter_err;
|
||||
}
|
||||
return 0;
|
||||
|
||||
i2c_get_adapter_err:
|
||||
gpiod_remove_lookup_table(&rg_gpio_lookup_table);
|
||||
platform_device_unregister(&i2c_gpio);
|
||||
gpiochip_remove(&xeon_gpio_chip);
|
||||
gpiod_remove_lookup_table(&rg_gpio_lookup_table);
|
||||
platform_device_unregister(&i2c_gpio);
|
||||
gpiochip_remove(&xeon_gpio_chip);
|
||||
|
||||
gpiochip_add_err:
|
||||
release_region(GPIO_BASE, GPIO_IOSIZE);
|
||||
return -1;
|
||||
release_region(GPIO_BASE, GPIO_IOSIZE);
|
||||
return -1;
|
||||
}
|
||||
|
||||
static void __exit xeon_gpio_exit(void)
|
||||
{
|
||||
gpiod_remove_lookup_table(&rg_gpio_lookup_table);
|
||||
platform_device_unregister(&i2c_gpio);
|
||||
mdelay(100);
|
||||
gpiochip_remove(&xeon_gpio_chip);
|
||||
release_region(GPIO_BASE, GPIO_IOSIZE);
|
||||
gpiod_remove_lookup_table(&rg_gpio_lookup_table);
|
||||
platform_device_unregister(&i2c_gpio);
|
||||
mdelay(100);
|
||||
gpiochip_remove(&xeon_gpio_chip);
|
||||
release_region(GPIO_BASE, GPIO_IOSIZE);
|
||||
}
|
||||
|
||||
module_init(xeon_gpio_init);
|
||||
|
@ -0,0 +1,734 @@
|
||||
/* -------------------------------------------------------------------------
|
||||
* i2c-algo-bit.c i2c driver algorithms for bit-shift adapters
|
||||
* -------------------------------------------------------------------------
|
||||
* Copyright (C) 1995-2000 Simon G. Vogl
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
* ------------------------------------------------------------------------- */
|
||||
|
||||
/* With some changes from Frodo Looijaard <frodol@dds.nl>, Kyösti Mälkki
|
||||
<kmalkki@cc.hut.fi> and Jean Delvare <jdelvare@suse.de> */
|
||||
|
||||
#include <linux/kernel.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/delay.h>
|
||||
#include <linux/errno.h>
|
||||
#include <linux/sched.h>
|
||||
#include <linux/i2c.h>
|
||||
#include <linux/i2c-algo-bit.h>
|
||||
|
||||
|
||||
/* ----- global defines ----------------------------------------------- */
|
||||
|
||||
#ifdef DEBUG
|
||||
#define bit_dbg(level, dev, format, args...) \
|
||||
do { \
|
||||
if (i2c_debug >= level) \
|
||||
dev_dbg(dev, format, ##args); \
|
||||
} while (0)
|
||||
#else
|
||||
#define bit_dbg(level, dev, format, args...) \
|
||||
do {} while (0)
|
||||
#endif /* DEBUG */
|
||||
|
||||
/* ----- global variables --------------------------------------------- */
|
||||
|
||||
static int bit_test; /* see if the line-setting functions work */
|
||||
module_param(bit_test, int, S_IRUGO);
|
||||
MODULE_PARM_DESC(bit_test, "lines testing - 0 off; 1 report; 2 fail if stuck");
|
||||
|
||||
#ifdef DEBUG
|
||||
static int i2c_debug = 1;
|
||||
module_param(i2c_debug, int, S_IRUGO | S_IWUSR);
|
||||
MODULE_PARM_DESC(i2c_debug,
|
||||
"debug level - 0 off; 1 normal; 2 verbose; 3 very verbose");
|
||||
#endif
|
||||
|
||||
/* --- setting states on the bus with the right timing: --------------- */
|
||||
|
||||
#define setsda(adap, val) adap->setsda(adap->data, val)
|
||||
#define setscl(adap, val) adap->setscl(adap->data, val)
|
||||
#define getsda(adap) adap->getsda(adap->data)
|
||||
#define getscl(adap) adap->getscl(adap->data)
|
||||
|
||||
static inline void sdalo(struct i2c_algo_bit_data *adap)
|
||||
{
|
||||
setsda(adap, 0);
|
||||
udelay((adap->udelay + 1) / 2);
|
||||
}
|
||||
|
||||
static inline void sdahi(struct i2c_algo_bit_data *adap)
|
||||
{
|
||||
setsda(adap, 1);
|
||||
udelay((adap->udelay + 1) / 2);
|
||||
}
|
||||
|
||||
static inline void scllo(struct i2c_algo_bit_data *adap)
|
||||
{
|
||||
setscl(adap, 0);
|
||||
udelay(adap->udelay / 2);
|
||||
}
|
||||
|
||||
/*
|
||||
* Raise scl line, and do checking for delays. This is necessary for slower
|
||||
* devices.
|
||||
*/
|
||||
static int sclhi(struct i2c_algo_bit_data *adap)
|
||||
{
|
||||
unsigned long start;
|
||||
|
||||
setscl(adap, 1);
|
||||
|
||||
/* Not all adapters have scl sense line... */
|
||||
if (!adap->getscl)
|
||||
goto done;
|
||||
|
||||
start = jiffies;
|
||||
while (!getscl(adap)) {
|
||||
/* This hw knows how to read the clock line, so we wait
|
||||
* until it actually gets high. This is safer as some
|
||||
* chips may hold it low ("clock stretching") while they
|
||||
* are processing data internally.
|
||||
*/
|
||||
if (time_after(jiffies, start + adap->timeout)) {
|
||||
/* Test one last time, as we may have been preempted
|
||||
* between last check and timeout test.
|
||||
*/
|
||||
if (getscl(adap))
|
||||
break;
|
||||
return -ETIMEDOUT;
|
||||
}
|
||||
cpu_relax();
|
||||
}
|
||||
#ifdef DEBUG
|
||||
if (jiffies != start && i2c_debug >= 3)
|
||||
pr_debug("i2c-algo-bit: needed %ld jiffies for SCL to go high\n",
|
||||
jiffies - start);
|
||||
#endif
|
||||
|
||||
done:
|
||||
udelay(adap->udelay);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/* --- other auxiliary functions -------------------------------------- */
|
||||
static void i2c_start(struct i2c_algo_bit_data *adap)
|
||||
{
|
||||
/* assert: scl, sda are high */
|
||||
setsda(adap, 0);
|
||||
udelay(adap->udelay);
|
||||
scllo(adap);
|
||||
}
|
||||
|
||||
static void i2c_repstart(struct i2c_algo_bit_data *adap)
|
||||
{
|
||||
/* assert: scl is low */
|
||||
sdahi(adap);
|
||||
sclhi(adap);
|
||||
setsda(adap, 0);
|
||||
udelay(adap->udelay);
|
||||
scllo(adap);
|
||||
}
|
||||
|
||||
|
||||
static void i2c_stop(struct i2c_algo_bit_data *adap)
|
||||
{
|
||||
/* assert: scl is low */
|
||||
sdalo(adap);
|
||||
sclhi(adap);
|
||||
setsda(adap, 1);
|
||||
udelay(adap->udelay);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* send a byte without start cond., look for arbitration,
|
||||
check ackn. from slave */
|
||||
/* returns:
|
||||
* 1 if the device acknowledged
|
||||
* 0 if the device did not ack
|
||||
* -ETIMEDOUT if an error occurred (while raising the scl line)
|
||||
*/
|
||||
static int i2c_outb(struct i2c_adapter *i2c_adap, unsigned char c)
|
||||
{
|
||||
int i;
|
||||
int sb;
|
||||
int ack;
|
||||
struct i2c_algo_bit_data *adap = i2c_adap->algo_data;
|
||||
|
||||
/* assert: scl is low */
|
||||
for (i = 7; i >= 0; i--) {
|
||||
sb = (c >> i) & 1;
|
||||
setsda(adap, sb);
|
||||
udelay((adap->udelay + 1) / 2);
|
||||
if (sclhi(adap) < 0) { /* timed out */
|
||||
bit_dbg(1, &i2c_adap->dev,
|
||||
"i2c_outb: 0x%02x, timeout at bit #%d\n",
|
||||
(int)c, i);
|
||||
return -ETIMEDOUT;
|
||||
}
|
||||
/* FIXME do arbitration here:
|
||||
* if (sb && !getsda(adap)) -> ouch! Get out of here.
|
||||
*
|
||||
* Report a unique code, so higher level code can retry
|
||||
* the whole (combined) message and *NOT* issue STOP.
|
||||
*/
|
||||
scllo(adap);
|
||||
}
|
||||
sdahi(adap);
|
||||
if (sclhi(adap) < 0) { /* timeout */
|
||||
bit_dbg(1, &i2c_adap->dev,
|
||||
"i2c_outb: 0x%02x, timeout at ack\n", (int)c);
|
||||
return -ETIMEDOUT;
|
||||
}
|
||||
|
||||
/* read ack: SDA should be pulled down by slave, or it may
|
||||
* NAK (usually to report problems with the data we wrote).
|
||||
*/
|
||||
ack = !getsda(adap); /* ack: sda is pulled low -> success */
|
||||
bit_dbg(2, &i2c_adap->dev, "i2c_outb: 0x%02x %s\n", (int)c,
|
||||
ack ? "A" : "NA");
|
||||
|
||||
scllo(adap);
|
||||
return ack;
|
||||
/* assert: scl is low (sda undef) */
|
||||
}
|
||||
|
||||
|
||||
static int i2c_inb(struct i2c_adapter *i2c_adap)
|
||||
{
|
||||
/* read byte via i2c port, without start/stop sequence */
|
||||
/* acknowledge is sent in i2c_read. */
|
||||
int i;
|
||||
unsigned char indata = 0;
|
||||
struct i2c_algo_bit_data *adap = i2c_adap->algo_data;
|
||||
|
||||
/* assert: scl is low */
|
||||
sdahi(adap);
|
||||
for (i = 0; i < 8; i++) {
|
||||
if (sclhi(adap) < 0) { /* timeout */
|
||||
bit_dbg(1, &i2c_adap->dev,
|
||||
"i2c_inb: timeout at bit #%d\n",
|
||||
7 - i);
|
||||
return -ETIMEDOUT;
|
||||
}
|
||||
indata *= 2;
|
||||
if (getsda(adap))
|
||||
indata |= 0x01;
|
||||
setscl(adap, 0);
|
||||
udelay(i == 7 ? adap->udelay / 2 : adap->udelay);
|
||||
}
|
||||
/* assert: scl is low */
|
||||
return indata;
|
||||
}
|
||||
|
||||
/*
|
||||
* Sanity check for the adapter hardware - check the reaction of
|
||||
* the bus lines only if it seems to be idle.
|
||||
*/
|
||||
static int test_bus(struct i2c_adapter *i2c_adap)
|
||||
{
|
||||
struct i2c_algo_bit_data *adap = i2c_adap->algo_data;
|
||||
const char *name = i2c_adap->name;
|
||||
int scl, sda, ret;
|
||||
|
||||
if (adap->pre_xfer) {
|
||||
ret = adap->pre_xfer(i2c_adap);
|
||||
if (ret < 0)
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
if (adap->getscl == NULL)
|
||||
pr_info("%s: Testing SDA only, SCL is not readable\n", name);
|
||||
|
||||
sda = getsda(adap);
|
||||
scl = (adap->getscl == NULL) ? 1 : getscl(adap);
|
||||
if (!scl || !sda) {
|
||||
printk(KERN_WARNING
|
||||
"%s: bus seems to be busy (scl=%d, sda=%d)\n",
|
||||
name, scl, sda);
|
||||
goto bailout;
|
||||
}
|
||||
|
||||
sdalo(adap);
|
||||
sda = getsda(adap);
|
||||
scl = (adap->getscl == NULL) ? 1 : getscl(adap);
|
||||
if (sda) {
|
||||
printk(KERN_WARNING "%s: SDA stuck high!\n", name);
|
||||
goto bailout;
|
||||
}
|
||||
if (!scl) {
|
||||
printk(KERN_WARNING
|
||||
"%s: SCL unexpected low while pulling SDA low!\n",
|
||||
name);
|
||||
goto bailout;
|
||||
}
|
||||
|
||||
sdahi(adap);
|
||||
sda = getsda(adap);
|
||||
scl = (adap->getscl == NULL) ? 1 : getscl(adap);
|
||||
if (!sda) {
|
||||
printk(KERN_WARNING "%s: SDA stuck low!\n", name);
|
||||
goto bailout;
|
||||
}
|
||||
if (!scl) {
|
||||
printk(KERN_WARNING
|
||||
"%s: SCL unexpected low while pulling SDA high!\n",
|
||||
name);
|
||||
goto bailout;
|
||||
}
|
||||
|
||||
scllo(adap);
|
||||
sda = getsda(adap);
|
||||
scl = (adap->getscl == NULL) ? 0 : getscl(adap);
|
||||
if (scl) {
|
||||
printk(KERN_WARNING "%s: SCL stuck high!\n", name);
|
||||
goto bailout;
|
||||
}
|
||||
if (!sda) {
|
||||
printk(KERN_WARNING
|
||||
"%s: SDA unexpected low while pulling SCL low!\n",
|
||||
name);
|
||||
goto bailout;
|
||||
}
|
||||
|
||||
sclhi(adap);
|
||||
sda = getsda(adap);
|
||||
scl = (adap->getscl == NULL) ? 1 : getscl(adap);
|
||||
if (!scl) {
|
||||
printk(KERN_WARNING "%s: SCL stuck low!\n", name);
|
||||
goto bailout;
|
||||
}
|
||||
if (!sda) {
|
||||
printk(KERN_WARNING
|
||||
"%s: SDA unexpected low while pulling SCL high!\n",
|
||||
name);
|
||||
goto bailout;
|
||||
}
|
||||
|
||||
if (adap->post_xfer)
|
||||
adap->post_xfer(i2c_adap);
|
||||
|
||||
pr_info("%s: Test OK\n", name);
|
||||
return 0;
|
||||
bailout:
|
||||
sdahi(adap);
|
||||
sclhi(adap);
|
||||
|
||||
if (adap->post_xfer)
|
||||
adap->post_xfer(i2c_adap);
|
||||
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
/* ----- Utility functions
|
||||
*/
|
||||
|
||||
/* try_address tries to contact a chip for a number of
|
||||
* times before it gives up.
|
||||
* return values:
|
||||
* 1 chip answered
|
||||
* 0 chip did not answer
|
||||
* -x transmission error
|
||||
*/
|
||||
static int try_address(struct i2c_adapter *i2c_adap,
|
||||
unsigned char addr, int retries)
|
||||
{
|
||||
struct i2c_algo_bit_data *adap = i2c_adap->algo_data;
|
||||
int i, ret = 0;
|
||||
|
||||
for (i = 0; i <= retries; i++) {
|
||||
ret = i2c_outb(i2c_adap, addr);
|
||||
if (ret == 1 || i == retries)
|
||||
break;
|
||||
bit_dbg(3, &i2c_adap->dev, "emitting stop condition\n");
|
||||
i2c_stop(adap);
|
||||
udelay(adap->udelay);
|
||||
yield();
|
||||
bit_dbg(3, &i2c_adap->dev, "emitting start condition\n");
|
||||
i2c_start(adap);
|
||||
}
|
||||
if (i && ret)
|
||||
bit_dbg(1, &i2c_adap->dev,
|
||||
"Used %d tries to %s client at 0x%02x: %s\n", i + 1,
|
||||
addr & 1 ? "read from" : "write to", addr >> 1,
|
||||
ret == 1 ? "success" : "failed, timeout?");
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int sendbytes(struct i2c_adapter *i2c_adap, struct i2c_msg *msg)
|
||||
{
|
||||
const unsigned char *temp = msg->buf;
|
||||
int count = msg->len;
|
||||
unsigned short nak_ok = msg->flags & I2C_M_IGNORE_NAK;
|
||||
int retval;
|
||||
int wrcount = 0;
|
||||
|
||||
while (count > 0) {
|
||||
retval = i2c_outb(i2c_adap, *temp);
|
||||
|
||||
/* OK/ACK; or ignored NAK */
|
||||
if ((retval > 0) || (nak_ok && (retval == 0))) {
|
||||
count--;
|
||||
temp++;
|
||||
wrcount++;
|
||||
|
||||
/* A slave NAKing the master means the slave didn't like
|
||||
* something about the data it saw. For example, maybe
|
||||
* the SMBus PEC was wrong.
|
||||
*/
|
||||
} else if (retval == 0) {
|
||||
dev_err(&i2c_adap->dev, "sendbytes: NAK bailout.\n");
|
||||
return -EIO;
|
||||
|
||||
/* Timeout; or (someday) lost arbitration
|
||||
*
|
||||
* FIXME Lost ARB implies retrying the transaction from
|
||||
* the first message, after the "winning" master issues
|
||||
* its STOP. As a rule, upper layer code has no reason
|
||||
* to know or care about this ... it is *NOT* an error.
|
||||
*/
|
||||
} else {
|
||||
dev_err(&i2c_adap->dev, "sendbytes: error %d\n",
|
||||
retval);
|
||||
return retval;
|
||||
}
|
||||
}
|
||||
return wrcount;
|
||||
}
|
||||
|
||||
static int acknak(struct i2c_adapter *i2c_adap, int is_ack)
|
||||
{
|
||||
struct i2c_algo_bit_data *adap = i2c_adap->algo_data;
|
||||
|
||||
/* assert: sda is high */
|
||||
if (is_ack) /* send ack */
|
||||
setsda(adap, 0);
|
||||
udelay((adap->udelay + 1) / 2);
|
||||
if (sclhi(adap) < 0) { /* timeout */
|
||||
dev_err(&i2c_adap->dev, "readbytes: ack/nak timeout\n");
|
||||
return -ETIMEDOUT;
|
||||
}
|
||||
scllo(adap);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int readbytes(struct i2c_adapter *i2c_adap, struct i2c_msg *msg)
|
||||
{
|
||||
int inval;
|
||||
int rdcount = 0; /* counts bytes read */
|
||||
unsigned char *temp = msg->buf;
|
||||
int count = msg->len;
|
||||
const unsigned flags = msg->flags;
|
||||
|
||||
while (count > 0) {
|
||||
inval = i2c_inb(i2c_adap);
|
||||
if (inval >= 0) {
|
||||
*temp = inval;
|
||||
rdcount++;
|
||||
} else { /* read timed out */
|
||||
break;
|
||||
}
|
||||
|
||||
temp++;
|
||||
count--;
|
||||
|
||||
/* Some SMBus transactions require that we receive the
|
||||
transaction length as the first read byte. */
|
||||
if (rdcount == 1 && (flags & I2C_M_RECV_LEN)) {
|
||||
if (inval <= 0 || inval > I2C_SMBUS_BLOCK_MAX) {
|
||||
if (!(flags & I2C_M_NO_RD_ACK))
|
||||
acknak(i2c_adap, 0);
|
||||
dev_err(&i2c_adap->dev,
|
||||
"readbytes: invalid block length (%d)\n",
|
||||
inval);
|
||||
return -EPROTO;
|
||||
}
|
||||
/* The original count value accounts for the extra
|
||||
bytes, that is, either 1 for a regular transaction,
|
||||
or 2 for a PEC transaction. */
|
||||
count += inval;
|
||||
msg->len += inval;
|
||||
}
|
||||
|
||||
bit_dbg(2, &i2c_adap->dev, "readbytes: 0x%02x %s\n",
|
||||
inval,
|
||||
(flags & I2C_M_NO_RD_ACK)
|
||||
? "(no ack/nak)"
|
||||
: (count ? "A" : "NA"));
|
||||
|
||||
if (!(flags & I2C_M_NO_RD_ACK)) {
|
||||
inval = acknak(i2c_adap, count);
|
||||
if (inval < 0)
|
||||
return inval;
|
||||
}
|
||||
}
|
||||
return rdcount;
|
||||
}
|
||||
|
||||
/* doAddress initiates the transfer by generating the start condition (in
|
||||
* try_address) and transmits the address in the necessary format to handle
|
||||
* reads, writes as well as 10bit-addresses.
|
||||
* returns:
|
||||
* 0 everything went okay, the chip ack'ed, or IGNORE_NAK flag was set
|
||||
* -x an error occurred (like: -ENXIO if the device did not answer, or
|
||||
* -ETIMEDOUT, for example if the lines are stuck...)
|
||||
*/
|
||||
static int bit_doAddress(struct i2c_adapter *i2c_adap, struct i2c_msg *msg)
|
||||
{
|
||||
unsigned short flags = msg->flags;
|
||||
unsigned short nak_ok = msg->flags & I2C_M_IGNORE_NAK;
|
||||
struct i2c_algo_bit_data *adap = i2c_adap->algo_data;
|
||||
|
||||
unsigned char addr;
|
||||
int ret, retries;
|
||||
|
||||
retries = nak_ok ? 0 : i2c_adap->retries;
|
||||
|
||||
if (flags & I2C_M_TEN) {
|
||||
/* a ten bit address */
|
||||
addr = 0xf0 | ((msg->addr >> 7) & 0x06);
|
||||
bit_dbg(2, &i2c_adap->dev, "addr0: %d\n", addr);
|
||||
/* try extended address code...*/
|
||||
ret = try_address(i2c_adap, addr, retries);
|
||||
if ((ret != 1) && !nak_ok) {
|
||||
dev_err(&i2c_adap->dev,
|
||||
"died at extended address code\n");
|
||||
return -ENXIO;
|
||||
}
|
||||
/* the remaining 8 bit address */
|
||||
ret = i2c_outb(i2c_adap, msg->addr & 0xff);
|
||||
if ((ret != 1) && !nak_ok) {
|
||||
/* the chip did not ack / xmission error occurred */
|
||||
dev_err(&i2c_adap->dev, "died at 2nd address code\n");
|
||||
return -ENXIO;
|
||||
}
|
||||
if (flags & I2C_M_RD) {
|
||||
bit_dbg(3, &i2c_adap->dev,
|
||||
"emitting repeated start condition\n");
|
||||
i2c_repstart(adap);
|
||||
/* okay, now switch into reading mode */
|
||||
addr |= 0x01;
|
||||
ret = try_address(i2c_adap, addr, retries);
|
||||
if ((ret != 1) && !nak_ok) {
|
||||
dev_err(&i2c_adap->dev,
|
||||
"died at repeated address code\n");
|
||||
return -EIO;
|
||||
}
|
||||
}
|
||||
} else { /* normal 7bit address */
|
||||
addr = i2c_8bit_addr_from_msg(msg);
|
||||
if (flags & I2C_M_REV_DIR_ADDR)
|
||||
addr ^= 1;
|
||||
ret = try_address(i2c_adap, addr, retries);
|
||||
if ((ret != 1) && !nak_ok)
|
||||
return -ENXIO;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void bit_i2c_unblock(struct i2c_adapter *i2c_adap)
|
||||
{
|
||||
int i;
|
||||
struct i2c_algo_bit_data *adap = i2c_adap->algo_data;
|
||||
|
||||
for (i = 0; i < 9; i++) {
|
||||
setscl(adap, 0);
|
||||
udelay(5);
|
||||
setscl(adap, 1);
|
||||
udelay(5);
|
||||
}
|
||||
setscl(adap, 0);
|
||||
setsda(adap, 0);
|
||||
udelay(5);
|
||||
setscl(adap, 1);
|
||||
udelay(5);
|
||||
setsda(adap, 1);
|
||||
}
|
||||
|
||||
static int check_bit_i2c_unblock(struct i2c_adapter *i2c_adap)
|
||||
{
|
||||
struct i2c_algo_bit_data *adap = i2c_adap->algo_data;
|
||||
int sda, scl;
|
||||
|
||||
sda = getsda(adap);
|
||||
scl = getscl(adap);
|
||||
if ((sda == 0) && scl) {
|
||||
// I2C_ALGO_BIT_ERROR("SCL is high and SDA is low, send 9 clock to device.\n");
|
||||
bit_i2c_unblock(i2c_adap);
|
||||
}
|
||||
|
||||
sda = getsda(adap);
|
||||
scl = getscl(adap);
|
||||
if (sda && scl) {
|
||||
// I2C_ALGO_BIT_DEBUG("SCL and SDA are both high, i2c level check ok.\n");
|
||||
return 0;
|
||||
}
|
||||
dev_warn(&i2c_adap->dev, "Check i2c level failed, SCL %s, SDA %s.\n", scl ? "high" : "low", sda ? "high" : "low");
|
||||
return -EIO;
|
||||
}
|
||||
|
||||
static int bit_xfer(struct i2c_adapter *i2c_adap,
|
||||
struct i2c_msg msgs[], int num)
|
||||
{
|
||||
struct i2c_msg *pmsg;
|
||||
struct i2c_algo_bit_data *adap = i2c_adap->algo_data;
|
||||
int i, ret;
|
||||
unsigned short nak_ok;
|
||||
|
||||
if (adap->pre_xfer) {
|
||||
ret = adap->pre_xfer(i2c_adap);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (check_bit_i2c_unblock(i2c_adap) < 0) {
|
||||
// I2C_ALGO_BIT_ERROR("check i2c is block.\n");
|
||||
return -EIO;
|
||||
}
|
||||
|
||||
bit_dbg(3, &i2c_adap->dev, "emitting start condition\n");
|
||||
i2c_start(adap);
|
||||
for (i = 0; i < num; i++) {
|
||||
pmsg = &msgs[i];
|
||||
nak_ok = pmsg->flags & I2C_M_IGNORE_NAK;
|
||||
if (!(pmsg->flags & I2C_M_NOSTART)) {
|
||||
if (i) {
|
||||
if (msgs[i - 1].flags & I2C_M_STOP) {
|
||||
bit_dbg(3, &i2c_adap->dev,
|
||||
"emitting enforced stop/start condition\n");
|
||||
i2c_stop(adap);
|
||||
i2c_start(adap);
|
||||
} else {
|
||||
bit_dbg(3, &i2c_adap->dev,
|
||||
"emitting repeated start condition\n");
|
||||
i2c_repstart(adap);
|
||||
}
|
||||
}
|
||||
ret = bit_doAddress(i2c_adap, pmsg);
|
||||
if ((ret != 0) && !nak_ok) {
|
||||
bit_dbg(1, &i2c_adap->dev,
|
||||
"NAK from device addr 0x%02x msg #%d\n",
|
||||
msgs[i].addr, i);
|
||||
goto bailout;
|
||||
}
|
||||
}
|
||||
if (pmsg->flags & I2C_M_RD) {
|
||||
/* read bytes into buffer*/
|
||||
ret = readbytes(i2c_adap, pmsg);
|
||||
if (ret >= 1)
|
||||
bit_dbg(2, &i2c_adap->dev, "read %d byte%s\n",
|
||||
ret, ret == 1 ? "" : "s");
|
||||
if (ret < pmsg->len) {
|
||||
if (ret >= 0)
|
||||
ret = -EIO;
|
||||
goto bailout;
|
||||
}
|
||||
} else {
|
||||
/* write bytes from buffer */
|
||||
ret = sendbytes(i2c_adap, pmsg);
|
||||
if (ret >= 1)
|
||||
bit_dbg(2, &i2c_adap->dev, "wrote %d byte%s\n",
|
||||
ret, ret == 1 ? "" : "s");
|
||||
if (ret < pmsg->len) {
|
||||
if (ret >= 0)
|
||||
ret = -EIO;
|
||||
goto bailout;
|
||||
}
|
||||
}
|
||||
}
|
||||
ret = i;
|
||||
|
||||
bailout:
|
||||
bit_dbg(3, &i2c_adap->dev, "emitting stop condition\n");
|
||||
i2c_stop(adap);
|
||||
|
||||
if (adap->post_xfer)
|
||||
adap->post_xfer(i2c_adap);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static u32 bit_func(struct i2c_adapter *adap)
|
||||
{
|
||||
return I2C_FUNC_I2C | I2C_FUNC_NOSTART | I2C_FUNC_SMBUS_EMUL |
|
||||
I2C_FUNC_SMBUS_READ_BLOCK_DATA |
|
||||
I2C_FUNC_SMBUS_BLOCK_PROC_CALL |
|
||||
I2C_FUNC_10BIT_ADDR | I2C_FUNC_PROTOCOL_MANGLING;
|
||||
}
|
||||
|
||||
|
||||
/* -----exported algorithm data: ------------------------------------- */
|
||||
|
||||
const struct i2c_algorithm rg_i2c_bit_algo = {
|
||||
.master_xfer = bit_xfer,
|
||||
.functionality = bit_func,
|
||||
};
|
||||
EXPORT_SYMBOL(rg_i2c_bit_algo);
|
||||
|
||||
static const struct i2c_adapter_quirks i2c_bit_quirk_no_clk_stretch = {
|
||||
.flags = I2C_AQ_NO_CLK_STRETCH,
|
||||
};
|
||||
|
||||
/*
|
||||
* registering functions to load algorithms at runtime
|
||||
*/
|
||||
static int __i2c_bit_add_bus(struct i2c_adapter *adap,
|
||||
int (*add_adapter)(struct i2c_adapter *))
|
||||
{
|
||||
struct i2c_algo_bit_data *bit_adap = adap->algo_data;
|
||||
int ret;
|
||||
|
||||
if (bit_test) {
|
||||
ret = test_bus(adap);
|
||||
if (bit_test >= 2 && ret < 0)
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
/* register new adapter to i2c module... */
|
||||
adap->algo = &rg_i2c_bit_algo;
|
||||
adap->retries = 3;
|
||||
if (bit_adap->getscl == NULL)
|
||||
adap->quirks = &i2c_bit_quirk_no_clk_stretch;
|
||||
|
||||
/*
|
||||
* We tried forcing SCL/SDA to an initial state here. But that caused a
|
||||
* regression, sadly. Check Bugzilla #200045 for details.
|
||||
*/
|
||||
|
||||
ret = add_adapter(adap);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
|
||||
/* Complain if SCL can't be read */
|
||||
if (bit_adap->getscl == NULL) {
|
||||
dev_warn(&adap->dev, "Not I2C compliant: can't read SCL\n");
|
||||
dev_warn(&adap->dev, "Bus may be unreliable\n");
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int rg_i2c_bit_add_bus(struct i2c_adapter *adap)
|
||||
{
|
||||
return __i2c_bit_add_bus(adap, i2c_add_adapter);
|
||||
}
|
||||
EXPORT_SYMBOL(rg_i2c_bit_add_bus);
|
||||
|
||||
int rg_i2c_bit_add_numbered_bus(struct i2c_adapter *adap)
|
||||
{
|
||||
return __i2c_bit_add_bus(adap, i2c_add_numbered_adapter);
|
||||
}
|
||||
EXPORT_SYMBOL(rg_i2c_bit_add_numbered_bus);
|
||||
|
||||
MODULE_AUTHOR("Simon G. Vogl <simon@tk.uni-linz.ac.at>");
|
||||
MODULE_DESCRIPTION("I2C-Bus bit-banging algorithm");
|
||||
MODULE_LICENSE("GPL");
|
@ -0,0 +1,431 @@
|
||||
/*
|
||||
* Bitbanging I2C bus driver using the GPIO API
|
||||
*
|
||||
* Copyright (C) 2007 Atmel Corporation
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
* published by the Free Software Foundation.
|
||||
*/
|
||||
#include <linux/debugfs.h>
|
||||
#include <linux/delay.h>
|
||||
#include <linux/i2c.h>
|
||||
#include <linux/i2c-algo-bit.h>
|
||||
#include <linux/platform_data/i2c-gpio.h>
|
||||
#include <linux/init.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/slab.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/gpio/consumer.h>
|
||||
#include <linux/of.h>
|
||||
|
||||
extern int rg_i2c_bit_add_numbered_bus(struct i2c_adapter *adap);
|
||||
|
||||
struct i2c_gpio_private_data {
|
||||
struct gpio_desc *sda;
|
||||
struct gpio_desc *scl;
|
||||
struct i2c_adapter adap;
|
||||
struct i2c_algo_bit_data bit_data;
|
||||
struct i2c_gpio_platform_data pdata;
|
||||
#ifdef CONFIG_I2C_GPIO_FAULT_INJECTOR
|
||||
struct dentry *debug_dir;
|
||||
#endif
|
||||
};
|
||||
|
||||
/*
|
||||
* Toggle SDA by changing the output value of the pin. This is only
|
||||
* valid for pins configured as open drain (i.e. setting the value
|
||||
* high effectively turns off the output driver.)
|
||||
*/
|
||||
static void i2c_gpio_setsda_val(void *data, int state)
|
||||
{
|
||||
struct i2c_gpio_private_data *priv = data;
|
||||
|
||||
gpiod_set_value_cansleep(priv->sda, state);
|
||||
}
|
||||
|
||||
/*
|
||||
* Toggle SCL by changing the output value of the pin. This is used
|
||||
* for pins that are configured as open drain and for output-only
|
||||
* pins. The latter case will break the i2c protocol, but it will
|
||||
* often work in practice.
|
||||
*/
|
||||
static void i2c_gpio_setscl_val(void *data, int state)
|
||||
{
|
||||
struct i2c_gpio_private_data *priv = data;
|
||||
|
||||
gpiod_set_value_cansleep(priv->scl, state);
|
||||
}
|
||||
|
||||
static int i2c_gpio_getsda(void *data)
|
||||
{
|
||||
struct i2c_gpio_private_data *priv = data;
|
||||
|
||||
return gpiod_get_value_cansleep(priv->sda);
|
||||
}
|
||||
|
||||
static int i2c_gpio_getscl(void *data)
|
||||
{
|
||||
struct i2c_gpio_private_data *priv = data;
|
||||
|
||||
return gpiod_get_value_cansleep(priv->scl);
|
||||
}
|
||||
|
||||
#ifdef CONFIG_I2C_GPIO_FAULT_INJECTOR
|
||||
static struct dentry *i2c_gpio_debug_dir;
|
||||
|
||||
#define setsda(bd, val) ((bd)->setsda((bd)->data, val))
|
||||
#define setscl(bd, val) ((bd)->setscl((bd)->data, val))
|
||||
#define getsda(bd) ((bd)->getsda((bd)->data))
|
||||
#define getscl(bd) ((bd)->getscl((bd)->data))
|
||||
|
||||
#define WIRE_ATTRIBUTE(wire) \
|
||||
static int fops_##wire##_get(void *data, u64 *val) \
|
||||
{ \
|
||||
struct i2c_gpio_private_data *priv = data; \
|
||||
\
|
||||
i2c_lock_bus(&priv->adap, I2C_LOCK_ROOT_ADAPTER); \
|
||||
*val = get##wire(&priv->bit_data); \
|
||||
i2c_unlock_bus(&priv->adap, I2C_LOCK_ROOT_ADAPTER); \
|
||||
return 0; \
|
||||
} \
|
||||
static int fops_##wire##_set(void *data, u64 val) \
|
||||
{ \
|
||||
struct i2c_gpio_private_data *priv = data; \
|
||||
\
|
||||
i2c_lock_bus(&priv->adap, I2C_LOCK_ROOT_ADAPTER); \
|
||||
set##wire(&priv->bit_data, val); \
|
||||
i2c_unlock_bus(&priv->adap, I2C_LOCK_ROOT_ADAPTER); \
|
||||
return 0; \
|
||||
} \
|
||||
DEFINE_DEBUGFS_ATTRIBUTE(fops_##wire, fops_##wire##_get, fops_##wire##_set, "%llu\n")
|
||||
|
||||
WIRE_ATTRIBUTE(scl);
|
||||
WIRE_ATTRIBUTE(sda);
|
||||
|
||||
static void i2c_gpio_incomplete_transfer(struct i2c_gpio_private_data *priv,
|
||||
u32 pattern, u8 pattern_size)
|
||||
{
|
||||
struct i2c_algo_bit_data *bit_data = &priv->bit_data;
|
||||
int i;
|
||||
|
||||
i2c_lock_bus(&priv->adap, I2C_LOCK_ROOT_ADAPTER);
|
||||
|
||||
/* START condition */
|
||||
setsda(bit_data, 0);
|
||||
udelay(bit_data->udelay);
|
||||
|
||||
/* Send pattern, request ACK, don't send STOP */
|
||||
for (i = pattern_size - 1; i >= 0; i--) {
|
||||
setscl(bit_data, 0);
|
||||
udelay(bit_data->udelay / 2);
|
||||
setsda(bit_data, (pattern >> i) & 1);
|
||||
udelay((bit_data->udelay + 1) / 2);
|
||||
setscl(bit_data, 1);
|
||||
udelay(bit_data->udelay);
|
||||
}
|
||||
|
||||
i2c_unlock_bus(&priv->adap, I2C_LOCK_ROOT_ADAPTER);
|
||||
}
|
||||
|
||||
static int fops_incomplete_addr_phase_set(void *data, u64 addr)
|
||||
{
|
||||
struct i2c_gpio_private_data *priv = data;
|
||||
u32 pattern;
|
||||
|
||||
if (addr > 0x7f)
|
||||
return -EINVAL;
|
||||
|
||||
/* ADDR (7 bit) + RD (1 bit) + Client ACK, keep SDA hi (1 bit) */
|
||||
pattern = (addr << 2) | 3;
|
||||
|
||||
i2c_gpio_incomplete_transfer(priv, pattern, 9);
|
||||
|
||||
return 0;
|
||||
}
|
||||
DEFINE_DEBUGFS_ATTRIBUTE(fops_incomplete_addr_phase, NULL, fops_incomplete_addr_phase_set, "%llu\n");
|
||||
|
||||
static int fops_incomplete_write_byte_set(void *data, u64 addr)
|
||||
{
|
||||
struct i2c_gpio_private_data *priv = data;
|
||||
u32 pattern;
|
||||
|
||||
if (addr > 0x7f)
|
||||
return -EINVAL;
|
||||
|
||||
/* ADDR (7 bit) + WR (1 bit) + Client ACK (1 bit) */
|
||||
pattern = (addr << 2) | 1;
|
||||
/* 0x00 (8 bit) + Client ACK, keep SDA hi (1 bit) */
|
||||
pattern = (pattern << 9) | 1;
|
||||
|
||||
i2c_gpio_incomplete_transfer(priv, pattern, 18);
|
||||
|
||||
return 0;
|
||||
}
|
||||
DEFINE_DEBUGFS_ATTRIBUTE(fops_incomplete_write_byte, NULL, fops_incomplete_write_byte_set, "%llu\n");
|
||||
|
||||
static void i2c_gpio_fault_injector_init(struct platform_device *pdev)
|
||||
{
|
||||
struct i2c_gpio_private_data *priv = platform_get_drvdata(pdev);
|
||||
|
||||
/*
|
||||
* If there will be a debugfs-dir per i2c adapter somewhen, put the
|
||||
* 'fault-injector' dir there. Until then, we have a global dir with
|
||||
* all adapters as subdirs.
|
||||
*/
|
||||
if (!i2c_gpio_debug_dir) {
|
||||
i2c_gpio_debug_dir = debugfs_create_dir("i2c-fault-injector", NULL);
|
||||
if (!i2c_gpio_debug_dir)
|
||||
return;
|
||||
}
|
||||
|
||||
priv->debug_dir = debugfs_create_dir(pdev->name, i2c_gpio_debug_dir);
|
||||
if (!priv->debug_dir)
|
||||
return;
|
||||
|
||||
debugfs_create_file_unsafe("scl", 0600, priv->debug_dir, priv, &fops_scl);
|
||||
debugfs_create_file_unsafe("sda", 0600, priv->debug_dir, priv, &fops_sda);
|
||||
debugfs_create_file_unsafe("incomplete_address_phase", 0200, priv->debug_dir,
|
||||
priv, &fops_incomplete_addr_phase);
|
||||
debugfs_create_file_unsafe("incomplete_write_byte", 0200, priv->debug_dir,
|
||||
priv, &fops_incomplete_write_byte);
|
||||
}
|
||||
|
||||
static void i2c_gpio_fault_injector_exit(struct platform_device *pdev)
|
||||
{
|
||||
struct i2c_gpio_private_data *priv = platform_get_drvdata(pdev);
|
||||
|
||||
debugfs_remove_recursive(priv->debug_dir);
|
||||
}
|
||||
#else
|
||||
static inline void i2c_gpio_fault_injector_init(struct platform_device *pdev) {}
|
||||
static inline void i2c_gpio_fault_injector_exit(struct platform_device *pdev) {}
|
||||
#endif /* CONFIG_I2C_GPIO_FAULT_INJECTOR*/
|
||||
|
||||
static void of_i2c_gpio_get_props(struct device_node *np,
|
||||
struct i2c_gpio_platform_data *pdata)
|
||||
{
|
||||
u32 reg;
|
||||
|
||||
of_property_read_u32(np, "i2c-gpio,delay-us", &pdata->udelay);
|
||||
|
||||
if (!of_property_read_u32(np, "i2c-gpio,timeout-ms", ®))
|
||||
pdata->timeout = msecs_to_jiffies(reg);
|
||||
|
||||
pdata->sda_is_open_drain =
|
||||
of_property_read_bool(np, "i2c-gpio,sda-open-drain");
|
||||
pdata->scl_is_open_drain =
|
||||
of_property_read_bool(np, "i2c-gpio,scl-open-drain");
|
||||
pdata->scl_is_output_only =
|
||||
of_property_read_bool(np, "i2c-gpio,scl-output-only");
|
||||
}
|
||||
|
||||
static struct gpio_desc *i2c_gpio_get_desc(struct device *dev,
|
||||
const char *con_id,
|
||||
unsigned int index,
|
||||
enum gpiod_flags gflags)
|
||||
{
|
||||
struct gpio_desc *retdesc;
|
||||
int ret;
|
||||
|
||||
retdesc = devm_gpiod_get(dev, con_id, gflags);
|
||||
if (!IS_ERR(retdesc)) {
|
||||
dev_dbg(dev, "got GPIO from name %s\n", con_id);
|
||||
return retdesc;
|
||||
}
|
||||
|
||||
retdesc = devm_gpiod_get_index(dev, NULL, index, gflags);
|
||||
if (!IS_ERR(retdesc)) {
|
||||
dev_dbg(dev, "got GPIO from index %u\n", index);
|
||||
return retdesc;
|
||||
}
|
||||
|
||||
ret = PTR_ERR(retdesc);
|
||||
|
||||
/* FIXME: hack in the old code, is this really necessary? */
|
||||
if (ret == -EINVAL)
|
||||
retdesc = ERR_PTR(-EPROBE_DEFER);
|
||||
|
||||
/* This happens if the GPIO driver is not yet probed, let's defer */
|
||||
if (ret == -ENOENT)
|
||||
retdesc = ERR_PTR(-EPROBE_DEFER);
|
||||
|
||||
if (PTR_ERR(retdesc) != -EPROBE_DEFER)
|
||||
dev_err(dev, "error trying to get descriptor: %d\n", ret);
|
||||
|
||||
return retdesc;
|
||||
}
|
||||
|
||||
static int i2c_gpio_probe(struct platform_device *pdev)
|
||||
{
|
||||
struct i2c_gpio_private_data *priv;
|
||||
struct i2c_gpio_platform_data *pdata;
|
||||
struct i2c_algo_bit_data *bit_data;
|
||||
struct i2c_adapter *adap;
|
||||
struct device *dev = &pdev->dev;
|
||||
struct device_node *np = dev->of_node;
|
||||
enum gpiod_flags gflags;
|
||||
int ret;
|
||||
|
||||
priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
|
||||
if (!priv)
|
||||
return -ENOMEM;
|
||||
|
||||
adap = &priv->adap;
|
||||
bit_data = &priv->bit_data;
|
||||
pdata = &priv->pdata;
|
||||
|
||||
if (np) {
|
||||
of_i2c_gpio_get_props(np, pdata);
|
||||
} else {
|
||||
/*
|
||||
* If all platform data settings are zero it is OK
|
||||
* to not provide any platform data from the board.
|
||||
*/
|
||||
if (dev_get_platdata(dev))
|
||||
memcpy(pdata, dev_get_platdata(dev), sizeof(*pdata));
|
||||
}
|
||||
|
||||
/*
|
||||
* First get the GPIO pins; if it fails, we'll defer the probe.
|
||||
* If the SDA line is marked from platform data or device tree as
|
||||
* "open drain" it means something outside of our control is making
|
||||
* this line being handled as open drain, and we should just handle
|
||||
* it as any other output. Else we enforce open drain as this is
|
||||
* required for an I2C bus.
|
||||
*/
|
||||
if (pdata->sda_is_open_drain)
|
||||
gflags = GPIOD_OUT_HIGH;
|
||||
else
|
||||
gflags = GPIOD_OUT_HIGH_OPEN_DRAIN;
|
||||
priv->sda = i2c_gpio_get_desc(dev, "sda", 0, gflags);
|
||||
if (IS_ERR(priv->sda))
|
||||
return PTR_ERR(priv->sda);
|
||||
|
||||
/*
|
||||
* If the SCL line is marked from platform data or device tree as
|
||||
* "open drain" it means something outside of our control is making
|
||||
* this line being handled as open drain, and we should just handle
|
||||
* it as any other output. Else we enforce open drain as this is
|
||||
* required for an I2C bus.
|
||||
*/
|
||||
if (pdata->scl_is_open_drain)
|
||||
gflags = GPIOD_OUT_HIGH;
|
||||
else
|
||||
gflags = GPIOD_OUT_HIGH_OPEN_DRAIN;
|
||||
priv->scl = i2c_gpio_get_desc(dev, "scl", 1, gflags);
|
||||
if (IS_ERR(priv->scl))
|
||||
return PTR_ERR(priv->scl);
|
||||
|
||||
if (gpiod_cansleep(priv->sda) || gpiod_cansleep(priv->scl))
|
||||
dev_warn(dev, "Slow GPIO pins might wreak havoc into I2C/SMBus bus timing");
|
||||
|
||||
bit_data->setsda = i2c_gpio_setsda_val;
|
||||
bit_data->setscl = i2c_gpio_setscl_val;
|
||||
|
||||
if (!pdata->scl_is_output_only)
|
||||
bit_data->getscl = i2c_gpio_getscl;
|
||||
bit_data->getsda = i2c_gpio_getsda;
|
||||
|
||||
if (pdata->udelay)
|
||||
bit_data->udelay = pdata->udelay;
|
||||
else if (pdata->scl_is_output_only)
|
||||
bit_data->udelay = 50; /* 10 kHz */
|
||||
else
|
||||
bit_data->udelay = 5; /* 100 kHz */
|
||||
|
||||
if (pdata->timeout)
|
||||
bit_data->timeout = pdata->timeout;
|
||||
else
|
||||
bit_data->timeout = HZ / 10; /* 100 ms */
|
||||
|
||||
bit_data->data = priv;
|
||||
|
||||
adap->owner = THIS_MODULE;
|
||||
if (np)
|
||||
strlcpy(adap->name, dev_name(dev), sizeof(adap->name));
|
||||
else
|
||||
snprintf(adap->name, sizeof(adap->name), "i2c-gpio%d", pdev->id);
|
||||
|
||||
adap->algo_data = bit_data;
|
||||
adap->class = I2C_CLASS_HWMON | I2C_CLASS_SPD;
|
||||
adap->dev.parent = dev;
|
||||
adap->dev.of_node = np;
|
||||
|
||||
adap->nr = pdev->id;
|
||||
ret = rg_i2c_bit_add_numbered_bus(adap);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
platform_set_drvdata(pdev, priv);
|
||||
|
||||
/*
|
||||
* FIXME: using global GPIO numbers is not helpful. If/when we
|
||||
* get accessors to get the actual name of the GPIO line,
|
||||
* from the descriptor, then provide that instead.
|
||||
*/
|
||||
dev_info(dev, "using lines %u (SDA) and %u (SCL%s)\n",
|
||||
desc_to_gpio(priv->sda), desc_to_gpio(priv->scl),
|
||||
pdata->scl_is_output_only
|
||||
? ", no clock stretching" : "");
|
||||
|
||||
i2c_gpio_fault_injector_init(pdev);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int i2c_gpio_remove(struct platform_device *pdev)
|
||||
{
|
||||
struct i2c_gpio_private_data *priv;
|
||||
struct i2c_adapter *adap;
|
||||
|
||||
i2c_gpio_fault_injector_exit(pdev);
|
||||
|
||||
priv = platform_get_drvdata(pdev);
|
||||
adap = &priv->adap;
|
||||
|
||||
i2c_del_adapter(adap);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
#if defined(CONFIG_OF)
|
||||
static const struct of_device_id i2c_gpio_dt_ids[] = {
|
||||
{ .compatible = "rg-i2c-gpio", },
|
||||
{ /* sentinel */ }
|
||||
};
|
||||
|
||||
MODULE_DEVICE_TABLE(of, i2c_gpio_dt_ids);
|
||||
#endif
|
||||
|
||||
static struct platform_driver i2c_gpio_driver = {
|
||||
.driver = {
|
||||
.name = "rg-i2c-gpio",
|
||||
.of_match_table = of_match_ptr(i2c_gpio_dt_ids),
|
||||
},
|
||||
.probe = i2c_gpio_probe,
|
||||
.remove = i2c_gpio_remove,
|
||||
};
|
||||
|
||||
static int __init i2c_gpio_init(void)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret = platform_driver_register(&i2c_gpio_driver);
|
||||
if (ret)
|
||||
printk(KERN_ERR "i2c-gpio: probe failed: %d\n", ret);
|
||||
|
||||
return ret;
|
||||
}
|
||||
subsys_initcall(i2c_gpio_init);
|
||||
|
||||
static void __exit i2c_gpio_exit(void)
|
||||
{
|
||||
platform_driver_unregister(&i2c_gpio_driver);
|
||||
}
|
||||
module_exit(i2c_gpio_exit);
|
||||
|
||||
MODULE_AUTHOR("Haavard Skinnemoen (Atmel)");
|
||||
MODULE_DESCRIPTION("Platform-independent bitbanging I2C driver");
|
||||
MODULE_LICENSE("GPL");
|
||||
MODULE_ALIAS("platform:i2c-gpio");
|
@ -78,7 +78,7 @@ typedef enum dfd_dev_info_type_e {
|
||||
} dfd_dev_tlv_type_t;
|
||||
|
||||
typedef struct dfd_dev_head_info_s {
|
||||
uint8_t ver; /* define E2PROM version,default is 0x01 */
|
||||
uint8_t ver; /* define E2PROM version,default is 0x01 */
|
||||
uint8_t flag; /* flag is 0x7E in new version E2PROM */
|
||||
uint8_t hw_ver; /* consists of main version and revise version */
|
||||
uint8_t type; /* HW type */
|
||||
|
@ -5,7 +5,7 @@ import click
|
||||
import os
|
||||
import time
|
||||
from ragileconfig import GLOBALCONFIG, GLOBALINITPARAM, GLOBALINITCOMMAND, MAC_LED_RESET, STARTMODULE, i2ccheck_params
|
||||
from ragileutil import rgpciwr, os_system, rgi2cset
|
||||
from ragileutil import rgpciwr, os_system, rgi2cset, io_wr
|
||||
|
||||
CONTEXT_SETTINGS = dict(help_option_names=['-h', '--help'])
|
||||
|
||||
@ -154,7 +154,7 @@ def add_dev(name, bus, loc):
|
||||
if name == "lm75":
|
||||
time.sleep(0.1)
|
||||
pdevpath = "/sys/bus/i2c/devices/i2c-%d/" % (bus)
|
||||
for i in range(1, 100):#wait for mother-bus generation, maximum wait time is 10s
|
||||
for i in range(1, 100):#wait for mother-bus generation,maximum wait time is 10s
|
||||
if os.path.exists(pdevpath) == True:
|
||||
break
|
||||
time.sleep(0.1)
|
||||
@ -240,13 +240,16 @@ def adddrivers():
|
||||
|
||||
def otherinit():
|
||||
for index in GLOBALINITPARAM:
|
||||
# write_sysfs_value(index["loc"], index["value"])
|
||||
ret, _ = rgi2cset(
|
||||
index.get("bus"),
|
||||
index.get("devaddr"),
|
||||
index.get("offset"),
|
||||
index.get("val")
|
||||
)
|
||||
index_type = index.get("type", None)
|
||||
if index_type == "io":
|
||||
ret = io_wr(index.get("offset"), index.get("val"))
|
||||
else:
|
||||
ret, _ = rgi2cset(
|
||||
index.get("bus"),
|
||||
index.get("devaddr"),
|
||||
index.get("offset"),
|
||||
index.get("val")
|
||||
)
|
||||
if not ret:
|
||||
click.echo("%%DEVICE_I2C-INIT: init param %s failed." % index.get("name"))
|
||||
|
||||
|
@ -31,6 +31,8 @@ from ragileutil import (
|
||||
get_sysfs_value,
|
||||
strtoint,
|
||||
rgi2cset,
|
||||
io_rd,
|
||||
rgsysset,
|
||||
)
|
||||
|
||||
|
||||
@ -666,7 +668,7 @@ class FanControl(object):
|
||||
logger.error(str(e))
|
||||
return False
|
||||
|
||||
# device error algorithm Tmac-Tin >= 50, or Tmac-Tin <= -50
|
||||
# device error algorithm Tmac-Tin≥50℃, or Tmac-Tin≤-50℃
|
||||
def check_dev_err(self):
|
||||
try:
|
||||
if (self.mac_aver - self.intemp) >= MONITOR_CONST.MAC_UP_TEMP or (
|
||||
|
@ -211,6 +211,8 @@ MONITOR_INTERVAL = 60
|
||||
MONITOR_MAC_SOURCE_SYSFS = (0)
|
||||
MONITOR_MAC_SOURCE_PATH = None # sysfs path
|
||||
|
||||
|
||||
# default MAC AVS parameters
|
||||
MAC_AVS_PARAM = {
|
||||
0x72: 0x0384,
|
||||
0x73: 0x037E,
|
||||
@ -302,7 +304,7 @@ fanloc = {"name": "fanset", "location": "0-0032/fan_speed_set"}
|
||||
|
||||
####================================Adaption-Area================================
|
||||
#### RAGILE_COMMON common configuration head
|
||||
#### "platform" specific configuration head
|
||||
#### “platform” specific configuration head
|
||||
####
|
||||
PCA9548START = 11
|
||||
PCA9548BUSEND = 74
|
||||
|
@ -382,7 +382,7 @@ def getInputSetmac(val):
|
||||
|
||||
|
||||
class fan_tlv(object):
|
||||
VERSION = 0x01 # E2PROM Version, start from 0x01
|
||||
VERSION = 0x01 # E2PROM Version,start from 0x01
|
||||
FLAG = 0x7E # New E2PROM version flag is 0x7E
|
||||
HW_VER = 0x01 # compose by master version and fixed version
|
||||
TYPE = 0xF1 # hw type defination
|
||||
@ -1043,7 +1043,7 @@ def util_setmac(eth, mac):
|
||||
log_debug(ifconfigcmd)
|
||||
ret, status = os_system(ifconfigcmd)
|
||||
if ret:
|
||||
raise SETMACException("software set Internet cardMAC error")
|
||||
raise SETMACException("software set Internet card MAC error")
|
||||
index = 0
|
||||
for item in macs:
|
||||
cmd = "ethtool -E %s magic %s offset %d value 0x%s" % (eth, magic, index, item)
|
||||
@ -1051,7 +1051,7 @@ def util_setmac(eth, mac):
|
||||
index += 1
|
||||
ret, log = os_system(cmd)
|
||||
if ret != 0:
|
||||
raise SETMACException(" set hardware Internet card MAC error")
|
||||
raise SETMACException("set hardware Internet card MAC error")
|
||||
# get value after setting
|
||||
cmd_t = "ethtool -e eth0 offset 0 length 6"
|
||||
ret, log = os_system(cmd_t)
|
||||
@ -1224,13 +1224,15 @@ def rgpcird(pcibus, slot, fn, bar, offset):
|
||||
s = result[::-1]
|
||||
val = 0
|
||||
for i in range(0, len(s)):
|
||||
val = val << 8 | ord(s[i])
|
||||
val = val << 8 | s[i]
|
||||
return "0x%08x" % val
|
||||
|
||||
|
||||
def rgpciwr(pcibus, slot, fn, bar, offset, data):
|
||||
"""write pci register"""
|
||||
ret = inttostr(data, 4)
|
||||
ret = str.encode(ret)
|
||||
ret = ret.strip(b'\xc2')
|
||||
filename = "/sys/bus/pci/devices/0000:%02x:%02x.%x/resource%d" % (
|
||||
int(pcibus),
|
||||
int(slot),
|
||||
@ -1245,7 +1247,7 @@ def rgpciwr(pcibus, slot, fn, bar, offset, data):
|
||||
s = result[::-1]
|
||||
val = 0
|
||||
for i in range(0, len(s)):
|
||||
val = val << 8 | ord(s[i])
|
||||
val = val << 8 | s[i]
|
||||
data.close()
|
||||
|
||||
|
||||
@ -1293,13 +1295,14 @@ def fan_setmac():
|
||||
|
||||
def checkfansninput(fan_sn, fansntemp):
|
||||
if fan_sn in fansntemp:
|
||||
RJPRINTERR("exist same Serial Number, please input again")
|
||||
RJPRINTERR("exist same Serial Number,please input again")
|
||||
return False
|
||||
if len(fan_sn) != 13:
|
||||
RJPRINTERR("Serial Number length incorrect, please input again")
|
||||
RJPRINTERR("Serial Number length incorrect,please input again")
|
||||
return False
|
||||
return True
|
||||
|
||||
|
||||
# check hw version
|
||||
def checkfanhwinput(hw):
|
||||
if len(hw) != 4:
|
||||
@ -1413,7 +1416,7 @@ def fac_fans_setmac_tlv(ret):
|
||||
print("\n*******************************\n")
|
||||
|
||||
util_show_fanse2(fans)
|
||||
if getInputCheck("check input correctly or not(Yes/No):") == True:
|
||||
if getInputCheck("check input correctly or not(Yes/No):") == True:
|
||||
for fan in fans:
|
||||
log_debug("ouput fan")
|
||||
fac_fan_setmac(fan)
|
||||
@ -2051,30 +2054,27 @@ def get_version_config_info(attr_key, file_name=None):
|
||||
return None
|
||||
|
||||
|
||||
def io_rd(reg_addr, len=1):
|
||||
u"""io read"""
|
||||
def io_rd(reg_addr, size=1):
|
||||
path = "/dev/port"
|
||||
ret = ""
|
||||
fd = None
|
||||
try:
|
||||
regaddr = 0
|
||||
if type(reg_addr) == int:
|
||||
regaddr = reg_addr
|
||||
else:
|
||||
regaddr = int(reg_addr, 16)
|
||||
devfile = "/dev/port"
|
||||
fd = os.open(devfile, os.O_RDWR | os.O_CREAT)
|
||||
os.lseek(fd, regaddr, os.SEEK_SET)
|
||||
str = os.read(fd, len)
|
||||
return "".join(["%02x" % ord(item) for item in str])
|
||||
except ValueError:
|
||||
return None
|
||||
reg_addr = int(reg_addr)
|
||||
fd = os.open(path, os.O_RDWR|os.O_CREAT)
|
||||
for i in range(size):
|
||||
os.lseek(fd, reg_addr+i, os.SEEK_SET)
|
||||
ret+="{:02x}".format(ord(os.read(fd, 1).decode('latin-1')))
|
||||
return ret
|
||||
except Exception as e:
|
||||
print(e)
|
||||
print(str(e))
|
||||
return None
|
||||
finally:
|
||||
os.close(fd)
|
||||
if fd: os.close(fd)
|
||||
|
||||
|
||||
def io_wr(reg_addr, reg_data):
|
||||
u"""io write"""
|
||||
fd = None
|
||||
try:
|
||||
regdata = 0
|
||||
regaddr = 0
|
||||
@ -2089,7 +2089,7 @@ def io_wr(reg_addr, reg_data):
|
||||
devfile = "/dev/port"
|
||||
fd = os.open(devfile, os.O_RDWR | os.O_CREAT)
|
||||
os.lseek(fd, regaddr, os.SEEK_SET)
|
||||
os.write(fd, chr(regdata))
|
||||
os.write(fd, regdata.to_bytes(2, 'little'))
|
||||
return True
|
||||
except ValueError as e:
|
||||
print(e)
|
||||
@ -2098,4 +2098,4 @@ def io_wr(reg_addr, reg_data):
|
||||
print(e)
|
||||
return False
|
||||
finally:
|
||||
os.close(fd)
|
||||
if fd: os.close(fd)
|
||||
|
@ -11,3 +11,11 @@ Description: kernel modules for platform devices such as fan, led, sfp
|
||||
Package: platform-modules-ragile-ra-b6910-64c
|
||||
Architecture: amd64
|
||||
Description: kernel modules for platform devices such as fan, led, sfp
|
||||
|
||||
Package: platform-modules-ragile-ra-b6510-32c
|
||||
Architecture: amd64
|
||||
Description: kernel modules for platform devices such as fan, led, sfp
|
||||
|
||||
Package: platform-modules-ragile-ra-b6920-4s
|
||||
Architecture: amd64
|
||||
Description: kernel modules for platform devices such as fan, led, sfp
|
||||
|
@ -0,0 +1 @@
|
||||
ra-b6920-4s/scripts/pddf_post_device_create.sh /usr/local/bin
|
@ -2,5 +2,7 @@ currentdir = $(shell pwd)
|
||||
|
||||
MODULE_DIRS := ra-b6510-48v8c
|
||||
MODULE_DIRS += ra-b6910-64c
|
||||
MODULE_DIRS += ra-b6510-32c
|
||||
MODULE_DIRS += ra-b6920-4s
|
||||
|
||||
export MODULE_DIRS
|
||||
|
15
platform/broadcom/sonic-platform-modules-ragile/ra-b6510-32c/LICENSE
Executable file
15
platform/broadcom/sonic-platform-modules-ragile/ra-b6510-32c/LICENSE
Executable file
@ -0,0 +1,15 @@
|
||||
Copyright (C) 2016 Microsoft, Inc
|
||||
Copyright (C) 2018 Ragile Network Corporation
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user