rtl83xx-phy.c 110 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820182118221823182418251826182718281829183018311832183318341835183618371838183918401841184218431844184518461847184818491850185118521853185418551856185718581859186018611862186318641865186618671868186918701871187218731874187518761877187818791880188118821883188418851886188718881889189018911892189318941895189618971898189919001901190219031904190519061907190819091910191119121913191419151916191719181919192019211922192319241925192619271928192919301931193219331934193519361937193819391940194119421943194419451946194719481949195019511952195319541955195619571958195919601961196219631964196519661967196819691970197119721973197419751976197719781979198019811982198319841985198619871988198919901991199219931994199519961997199819992000200120022003200420052006200720082009201020112012201320142015201620172018201920202021202220232024202520262027202820292030203120322033203420352036203720382039204020412042204320442045204620472048204920502051205220532054205520562057205820592060206120622063206420652066206720682069207020712072207320742075207620772078207920802081208220832084208520862087208820892090209120922093209420952096209720982099210021012102210321042105210621072108210921102111211221132114211521162117211821192120212121222123212421252126212721282129213021312132213321342135213621372138213921402141214221432144214521462147214821492150215121522153215421552156215721582159216021612162216321642165216621672168216921702171217221732174217521762177217821792180218121822183218421852186218721882189219021912192219321942195219621972198219922002201220222032204220522062207220822092210221122122213221422152216221722182219222022212222222322242225222622272228222922302231223222332234223522362237223822392240224122422243224422452246224722482249225022512252225322542255225622572258225922602261226222632264226522662267226822692270227122722273227422752276227722782279228022812282228322842285228622872288228922902291229222932294229522962297229822992300230123022303230423052306230723082309231023112312231323142315231623172318231923202321232223232324232523262327232823292330233123322333233423352336233723382339234023412342234323442345234623472348234923502351235223532354235523562357235823592360236123622363236423652366236723682369237023712372237323742375237623772378237923802381238223832384238523862387238823892390239123922393239423952396239723982399240024012402240324042405240624072408240924102411241224132414241524162417241824192420242124222423242424252426242724282429243024312432243324342435243624372438243924402441244224432444244524462447244824492450245124522453245424552456245724582459246024612462246324642465246624672468246924702471247224732474247524762477247824792480248124822483248424852486248724882489249024912492249324942495249624972498249925002501250225032504250525062507250825092510251125122513251425152516251725182519252025212522252325242525252625272528252925302531253225332534253525362537253825392540254125422543254425452546254725482549255025512552255325542555255625572558255925602561256225632564256525662567256825692570257125722573257425752576257725782579258025812582258325842585258625872588258925902591259225932594259525962597259825992600260126022603260426052606260726082609261026112612261326142615261626172618261926202621262226232624262526262627262826292630263126322633263426352636263726382639264026412642264326442645264626472648264926502651265226532654265526562657265826592660266126622663266426652666266726682669267026712672267326742675267626772678267926802681268226832684268526862687268826892690269126922693269426952696269726982699270027012702270327042705270627072708270927102711271227132714271527162717271827192720272127222723272427252726272727282729273027312732273327342735273627372738273927402741274227432744274527462747274827492750275127522753275427552756275727582759276027612762276327642765276627672768276927702771277227732774277527762777277827792780278127822783278427852786278727882789279027912792279327942795279627972798279928002801280228032804280528062807280828092810281128122813281428152816281728182819282028212822282328242825282628272828282928302831283228332834283528362837283828392840284128422843284428452846284728482849285028512852285328542855285628572858285928602861286228632864286528662867286828692870287128722873287428752876287728782879288028812882288328842885288628872888288928902891289228932894289528962897289828992900290129022903290429052906290729082909291029112912291329142915291629172918291929202921292229232924292529262927292829292930293129322933293429352936293729382939294029412942294329442945294629472948294929502951295229532954295529562957295829592960296129622963296429652966296729682969297029712972297329742975297629772978297929802981298229832984298529862987298829892990299129922993299429952996299729982999300030013002300330043005300630073008300930103011301230133014301530163017301830193020302130223023302430253026302730283029303030313032303330343035303630373038303930403041304230433044304530463047304830493050305130523053305430553056305730583059306030613062306330643065306630673068306930703071307230733074307530763077307830793080308130823083308430853086308730883089309030913092309330943095309630973098309931003101310231033104310531063107310831093110311131123113311431153116311731183119312031213122312331243125312631273128312931303131313231333134313531363137313831393140314131423143314431453146314731483149315031513152315331543155315631573158315931603161316231633164316531663167316831693170317131723173317431753176317731783179318031813182318331843185318631873188318931903191319231933194319531963197319831993200320132023203320432053206320732083209321032113212321332143215321632173218321932203221322232233224322532263227322832293230323132323233323432353236323732383239324032413242324332443245324632473248324932503251325232533254325532563257325832593260326132623263326432653266326732683269327032713272327332743275327632773278327932803281328232833284328532863287328832893290329132923293329432953296329732983299330033013302330333043305330633073308330933103311331233133314331533163317331833193320332133223323332433253326332733283329333033313332333333343335333633373338333933403341334233433344334533463347334833493350335133523353335433553356335733583359336033613362336333643365336633673368336933703371337233733374337533763377337833793380338133823383338433853386338733883389339033913392339333943395339633973398339934003401340234033404340534063407340834093410341134123413341434153416341734183419342034213422342334243425342634273428342934303431343234333434343534363437343834393440344134423443344434453446344734483449345034513452345334543455345634573458345934603461346234633464346534663467346834693470347134723473347434753476347734783479348034813482348334843485348634873488348934903491349234933494349534963497349834993500350135023503350435053506350735083509351035113512351335143515351635173518351935203521352235233524352535263527352835293530353135323533353435353536353735383539354035413542354335443545354635473548354935503551355235533554355535563557355835593560356135623563356435653566356735683569357035713572357335743575357635773578357935803581358235833584358535863587358835893590359135923593359435953596359735983599360036013602360336043605360636073608360936103611361236133614361536163617361836193620362136223623362436253626362736283629363036313632363336343635363636373638363936403641364236433644364536463647364836493650365136523653365436553656365736583659366036613662366336643665366636673668366936703671367236733674367536763677367836793680368136823683368436853686368736883689369036913692369336943695369636973698369937003701370237033704370537063707370837093710371137123713371437153716371737183719372037213722372337243725372637273728372937303731373237333734373537363737373837393740374137423743374437453746374737483749375037513752375337543755375637573758375937603761376237633764376537663767376837693770377137723773377437753776377737783779378037813782378337843785378637873788378937903791379237933794379537963797379837993800380138023803380438053806380738083809381038113812381338143815381638173818381938203821382238233824382538263827382838293830383138323833383438353836383738383839384038413842384338443845384638473848384938503851385238533854385538563857385838593860386138623863386438653866386738683869387038713872387338743875387638773878387938803881388238833884388538863887388838893890389138923893389438953896389738983899390039013902390339043905390639073908390939103911391239133914391539163917391839193920392139223923392439253926392739283929393039313932393339343935393639373938393939403941394239433944394539463947394839493950395139523953395439553956395739583959396039613962396339643965396639673968396939703971397239733974397539763977397839793980398139823983398439853986
  1. // SPDX-License-Identifier: GPL-2.0-only
  2. /* Realtek RTL838X Ethernet MDIO interface driver
  3. *
  4. * Copyright (C) 2020 B. Koblitz
  5. */
  6. #include <linux/module.h>
  7. #include <linux/delay.h>
  8. #include <linux/of.h>
  9. #include <linux/phy.h>
  10. #include <linux/netdevice.h>
  11. #include <linux/firmware.h>
  12. #include <linux/crc32.h>
  13. #include <linux/sfp.h>
  14. #include <linux/mii.h>
  15. #include <linux/mdio.h>
  16. #include <asm/mach-rtl838x/mach-rtl83xx.h>
  17. #include "rtl83xx-phy.h"
  18. extern struct rtl83xx_soc_info soc_info;
  19. extern struct mutex smi_lock;
  20. #define PHY_PAGE_2 2
  21. #define PHY_PAGE_4 4
  22. /* all Clause-22 RealTek MDIO PHYs use register 0x1f for page select */
  23. #define RTL8XXX_PAGE_SELECT 0x1f
  24. #define RTL8XXX_PAGE_MAIN 0x0000
  25. #define RTL821X_PAGE_PORT 0x0266
  26. #define RTL821X_PAGE_POWER 0x0a40
  27. #define RTL821X_PAGE_GPHY 0x0a42
  28. #define RTL821X_PAGE_MAC 0x0a43
  29. #define RTL821X_PAGE_STATE 0x0b80
  30. #define RTL821X_PAGE_PATCH 0x0b82
  31. /* Using the special page 0xfff with the MDIO controller found in
  32. * RealTek SoCs allows to access the PHY in RAW mode, ie. bypassing
  33. * the cache and paging engine of the MDIO controller.
  34. */
  35. #define RTL83XX_PAGE_RAW 0x0fff
  36. /* internal RTL821X PHY uses register 0x1d to select media page */
  37. #define RTL821XINT_MEDIA_PAGE_SELECT 0x1d
  38. /* external RTL821X PHY uses register 0x1e to select media page */
  39. #define RTL821XEXT_MEDIA_PAGE_SELECT 0x1e
  40. #define RTL821X_MEDIA_PAGE_AUTO 0
  41. #define RTL821X_MEDIA_PAGE_COPPER 1
  42. #define RTL821X_MEDIA_PAGE_FIBRE 3
  43. #define RTL821X_MEDIA_PAGE_INTERNAL 8
  44. #define RTL9300_PHY_ID_MASK 0xf0ffffff
  45. /* RTL930X SerDes supports the following modes:
  46. * 0x02: SGMII 0x04: 1000BX_FIBER 0x05: FIBER100
  47. * 0x06: QSGMII 0x09: RSGMII 0x0d: USXGMII
  48. * 0x10: XSGMII 0x12: HISGMII 0x16: 2500Base_X
  49. * 0x17: RXAUI_LITE 0x19: RXAUI_PLUS 0x1a: 10G Base-R
  50. * 0x1b: 10GR1000BX_AUTO 0x1f: OFF
  51. */
  52. #define RTL930X_SDS_MODE_SGMII 0x02
  53. #define RTL930X_SDS_MODE_1000BASEX 0x04
  54. #define RTL930X_SDS_MODE_USXGMII 0x0d
  55. #define RTL930X_SDS_MODE_XGMII 0x10
  56. #define RTL930X_SDS_MODE_HSGMII 0x12
  57. #define RTL930X_SDS_MODE_2500BASEX 0x16
  58. #define RTL930X_SDS_MODE_10GBASER 0x1a
  59. #define RTL930X_SDS_OFF 0x1f
  60. #define RTL930X_SDS_MASK 0x1f
  61. /* This lock protects the state of the SoC automatically polling the PHYs over the SMI
  62. * bus to detect e.g. link and media changes. For operations on the PHYs such as
  63. * patching or other configuration changes such as EEE, polling needs to be disabled
  64. * since otherwise these operations may fails or lead to unpredictable results.
  65. */
  66. DEFINE_MUTEX(poll_lock);
  67. static const struct firmware rtl838x_8380_fw;
  68. static const struct firmware rtl838x_8214fc_fw;
  69. static const struct firmware rtl838x_8218b_fw;
  70. static u64 disable_polling(int port)
  71. {
  72. u64 saved_state;
  73. mutex_lock(&poll_lock);
  74. switch (soc_info.family) {
  75. case RTL8380_FAMILY_ID:
  76. saved_state = sw_r32(RTL838X_SMI_POLL_CTRL);
  77. sw_w32_mask(BIT(port), 0, RTL838X_SMI_POLL_CTRL);
  78. break;
  79. case RTL8390_FAMILY_ID:
  80. saved_state = sw_r32(RTL839X_SMI_PORT_POLLING_CTRL + 4);
  81. saved_state <<= 32;
  82. saved_state |= sw_r32(RTL839X_SMI_PORT_POLLING_CTRL);
  83. sw_w32_mask(BIT(port % 32), 0,
  84. RTL839X_SMI_PORT_POLLING_CTRL + ((port >> 5) << 2));
  85. break;
  86. case RTL9300_FAMILY_ID:
  87. saved_state = sw_r32(RTL930X_SMI_POLL_CTRL);
  88. sw_w32_mask(BIT(port), 0, RTL930X_SMI_POLL_CTRL);
  89. break;
  90. case RTL9310_FAMILY_ID:
  91. pr_warn("%s not implemented for RTL931X\n", __func__);
  92. break;
  93. }
  94. mutex_unlock(&poll_lock);
  95. return saved_state;
  96. }
  97. static int resume_polling(u64 saved_state)
  98. {
  99. mutex_lock(&poll_lock);
  100. switch (soc_info.family) {
  101. case RTL8380_FAMILY_ID:
  102. sw_w32(saved_state, RTL838X_SMI_POLL_CTRL);
  103. break;
  104. case RTL8390_FAMILY_ID:
  105. sw_w32(saved_state >> 32, RTL839X_SMI_PORT_POLLING_CTRL + 4);
  106. sw_w32(saved_state, RTL839X_SMI_PORT_POLLING_CTRL);
  107. break;
  108. case RTL9300_FAMILY_ID:
  109. sw_w32(saved_state, RTL930X_SMI_POLL_CTRL);
  110. break;
  111. case RTL9310_FAMILY_ID:
  112. pr_warn("%s not implemented for RTL931X\n", __func__);
  113. break;
  114. }
  115. mutex_unlock(&poll_lock);
  116. return 0;
  117. }
  118. static void rtl8380_int_phy_on_off(struct phy_device *phydev, bool on)
  119. {
  120. phy_modify(phydev, 0, BMCR_PDOWN, on ? 0 : BMCR_PDOWN);
  121. }
  122. static void rtl8380_rtl8214fc_on_off(struct phy_device *phydev, bool on)
  123. {
  124. /* fiber ports */
  125. phy_write_paged(phydev, RTL83XX_PAGE_RAW, RTL821XEXT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_FIBRE);
  126. phy_modify(phydev, 0x10, BMCR_PDOWN, on ? 0 : BMCR_PDOWN);
  127. /* copper ports */
  128. phy_write_paged(phydev, RTL83XX_PAGE_RAW, RTL821XEXT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_COPPER);
  129. phy_modify_paged(phydev, RTL821X_PAGE_POWER, 0x10, BMCR_PDOWN, on ? 0 : BMCR_PDOWN);
  130. }
  131. static void rtl8380_phy_reset(struct phy_device *phydev)
  132. {
  133. phy_modify(phydev, 0, BMCR_RESET, BMCR_RESET);
  134. }
  135. /* The access registers for SDS_MODE_SEL and the LSB for each SDS within */
  136. u16 rtl9300_sds_regs[] = { 0x0194, 0x0194, 0x0194, 0x0194, 0x02a0, 0x02a0, 0x02a0, 0x02a0,
  137. 0x02A4, 0x02A4, 0x0198, 0x0198 };
  138. u8 rtl9300_sds_lsb[] = { 0, 6, 12, 18, 0, 6, 12, 18, 0, 6, 0, 6};
  139. /* Reset the SerDes by powering it off and set a new operation mode
  140. * of the SerDes.
  141. */
  142. void rtl9300_sds_rst(int sds_num, u32 mode)
  143. {
  144. pr_info("%s %d\n", __func__, mode);
  145. if (sds_num < 0 || sds_num > 11) {
  146. pr_err("Wrong SerDes number: %d\n", sds_num);
  147. return;
  148. }
  149. sw_w32_mask(RTL930X_SDS_MASK << rtl9300_sds_lsb[sds_num],
  150. RTL930X_SDS_OFF << rtl9300_sds_lsb[sds_num],
  151. rtl9300_sds_regs[sds_num]);
  152. mdelay(10);
  153. sw_w32_mask(RTL930X_SDS_MASK << rtl9300_sds_lsb[sds_num], mode << rtl9300_sds_lsb[sds_num],
  154. rtl9300_sds_regs[sds_num]);
  155. mdelay(10);
  156. pr_debug("%s: 194:%08x 198:%08x 2a0:%08x 2a4:%08x\n", __func__,
  157. sw_r32(0x194), sw_r32(0x198), sw_r32(0x2a0), sw_r32(0x2a4));
  158. }
  159. void rtl9300_sds_set(int sds_num, u32 mode)
  160. {
  161. pr_info("%s %d\n", __func__, mode);
  162. if (sds_num < 0 || sds_num > 11) {
  163. pr_err("Wrong SerDes number: %d\n", sds_num);
  164. return;
  165. }
  166. sw_w32_mask(RTL930X_SDS_MASK << rtl9300_sds_lsb[sds_num], mode << rtl9300_sds_lsb[sds_num],
  167. rtl9300_sds_regs[sds_num]);
  168. mdelay(10);
  169. pr_debug("%s: 194:%08x 198:%08x 2a0:%08x 2a4:%08x\n", __func__,
  170. sw_r32(0x194), sw_r32(0x198), sw_r32(0x2a0), sw_r32(0x2a4));
  171. }
  172. u32 rtl9300_sds_mode_get(int sds_num)
  173. {
  174. u32 v;
  175. if (sds_num < 0 || sds_num > 11) {
  176. pr_err("Wrong SerDes number: %d\n", sds_num);
  177. return 0;
  178. }
  179. v = sw_r32(rtl9300_sds_regs[sds_num]);
  180. v >>= rtl9300_sds_lsb[sds_num];
  181. return v & RTL930X_SDS_MASK;
  182. }
  183. /* On the RTL839x family of SoCs with inbuilt SerDes, these SerDes are accessed through
  184. * a 2048 bit register that holds the contents of the PHY being simulated by the SoC.
  185. */
  186. int rtl839x_read_sds_phy(int phy_addr, int phy_reg)
  187. {
  188. int offset = 0;
  189. int reg;
  190. u32 val;
  191. if (phy_addr == 49)
  192. offset = 0x100;
  193. /* For the RTL8393 internal SerDes, we simulate a PHY ID in registers 2/3
  194. * which would otherwise read as 0.
  195. */
  196. if (soc_info.id == 0x8393) {
  197. if (phy_reg == MII_PHYSID1)
  198. return 0x1c;
  199. if (phy_reg == MII_PHYSID2)
  200. return 0x8393;
  201. }
  202. /* Register RTL839X_SDS12_13_XSG0 is 2048 bit broad, the MSB (bit 15) of the
  203. * 0th PHY register is bit 1023 (in byte 0x80). Because PHY-registers are 16
  204. * bit broad, we offset by reg << 1. In the SoC 2 registers are stored in
  205. * one 32 bit register.
  206. */
  207. reg = (phy_reg << 1) & 0xfc;
  208. val = sw_r32(RTL839X_SDS12_13_XSG0 + offset + 0x80 + reg);
  209. if (phy_reg & 1)
  210. val = (val >> 16) & 0xffff;
  211. else
  212. val &= 0xffff;
  213. return val;
  214. }
  215. /* On the RTL930x family of SoCs, the internal SerDes are accessed through an IO
  216. * register which simulates commands to an internal MDIO bus.
  217. */
  218. int rtl930x_read_sds_phy(int phy_addr, int page, int phy_reg)
  219. {
  220. int i;
  221. u32 cmd = phy_addr << 2 | page << 7 | phy_reg << 13 | 1;
  222. sw_w32(cmd, RTL930X_SDS_INDACS_CMD);
  223. for (i = 0; i < 100; i++) {
  224. if (!(sw_r32(RTL930X_SDS_INDACS_CMD) & 0x1))
  225. break;
  226. mdelay(1);
  227. }
  228. if (i >= 100)
  229. return -EIO;
  230. return sw_r32(RTL930X_SDS_INDACS_DATA) & 0xffff;
  231. }
  232. int rtl930x_write_sds_phy(int phy_addr, int page, int phy_reg, u16 v)
  233. {
  234. int i;
  235. u32 cmd;
  236. sw_w32(v, RTL930X_SDS_INDACS_DATA);
  237. cmd = phy_addr << 2 | page << 7 | phy_reg << 13 | 0x3;
  238. sw_w32(cmd, RTL930X_SDS_INDACS_CMD);
  239. for (i = 0; i < 100; i++) {
  240. if (!(sw_r32(RTL930X_SDS_INDACS_CMD) & 0x1))
  241. break;
  242. mdelay(1);
  243. }
  244. if (i >= 100) {
  245. pr_info("%s ERROR !!!!!!!!!!!!!!!!!!!!\n", __func__);
  246. return -EIO;
  247. }
  248. return 0;
  249. }
  250. int rtl931x_read_sds_phy(int phy_addr, int page, int phy_reg)
  251. {
  252. int i;
  253. u32 cmd = phy_addr << 2 | page << 7 | phy_reg << 13 | 1;
  254. pr_debug("%s: phy_addr(SDS-ID) %d, phy_reg: %d\n", __func__, phy_addr, phy_reg);
  255. sw_w32(cmd, RTL931X_SERDES_INDRT_ACCESS_CTRL);
  256. for (i = 0; i < 100; i++) {
  257. if (!(sw_r32(RTL931X_SERDES_INDRT_ACCESS_CTRL) & 0x1))
  258. break;
  259. mdelay(1);
  260. }
  261. if (i >= 100)
  262. return -EIO;
  263. pr_debug("%s: returning %04x\n", __func__, sw_r32(RTL931X_SERDES_INDRT_DATA_CTRL) & 0xffff);
  264. return sw_r32(RTL931X_SERDES_INDRT_DATA_CTRL) & 0xffff;
  265. }
  266. int rtl931x_write_sds_phy(int phy_addr, int page, int phy_reg, u16 v)
  267. {
  268. int i;
  269. u32 cmd;
  270. cmd = phy_addr << 2 | page << 7 | phy_reg << 13;
  271. sw_w32(cmd, RTL931X_SERDES_INDRT_ACCESS_CTRL);
  272. sw_w32(v, RTL931X_SERDES_INDRT_DATA_CTRL);
  273. cmd = sw_r32(RTL931X_SERDES_INDRT_ACCESS_CTRL) | 0x3;
  274. sw_w32(cmd, RTL931X_SERDES_INDRT_ACCESS_CTRL);
  275. for (i = 0; i < 100; i++) {
  276. if (!(sw_r32(RTL931X_SERDES_INDRT_ACCESS_CTRL) & 0x1))
  277. break;
  278. mdelay(1);
  279. }
  280. if (i >= 100)
  281. return -EIO;
  282. return 0;
  283. }
  284. /* On the RTL838x SoCs, the internal SerDes is accessed through direct access to
  285. * standard PHY registers, where a 32 bit register holds a 16 bit word as found
  286. * in a standard page 0 of a PHY
  287. */
  288. int rtl838x_read_sds_phy(int phy_addr, int phy_reg)
  289. {
  290. int offset = 0;
  291. u32 val;
  292. if (phy_addr == 26)
  293. offset = 0x100;
  294. val = sw_r32(RTL838X_SDS4_FIB_REG0 + offset + (phy_reg << 2)) & 0xffff;
  295. return val;
  296. }
  297. int rtl839x_write_sds_phy(int phy_addr, int phy_reg, u16 v)
  298. {
  299. int offset = 0;
  300. int reg;
  301. u32 val;
  302. if (phy_addr == 49)
  303. offset = 0x100;
  304. reg = (phy_reg << 1) & 0xfc;
  305. val = v;
  306. if (phy_reg & 1) {
  307. val = val << 16;
  308. sw_w32_mask(0xffff0000, val,
  309. RTL839X_SDS12_13_XSG0 + offset + 0x80 + reg);
  310. } else {
  311. sw_w32_mask(0xffff, val,
  312. RTL839X_SDS12_13_XSG0 + offset + 0x80 + reg);
  313. }
  314. return 0;
  315. }
  316. /* Read the link and speed status of the 2 internal SGMII/1000Base-X
  317. * ports of the RTL838x SoCs
  318. */
  319. static int rtl8380_read_status(struct phy_device *phydev)
  320. {
  321. int err;
  322. err = genphy_read_status(phydev);
  323. if (phydev->link) {
  324. phydev->speed = SPEED_1000;
  325. phydev->duplex = DUPLEX_FULL;
  326. }
  327. return err;
  328. }
  329. /* Read the link and speed status of the 2 internal SGMII/1000Base-X
  330. * ports of the RTL8393 SoC
  331. */
  332. static int rtl8393_read_status(struct phy_device *phydev)
  333. {
  334. int offset = 0;
  335. int err;
  336. int phy_addr = phydev->mdio.addr;
  337. u32 v;
  338. err = genphy_read_status(phydev);
  339. if (phy_addr == 49)
  340. offset = 0x100;
  341. if (phydev->link) {
  342. phydev->speed = SPEED_100;
  343. /* Read SPD_RD_00 (bit 13) and SPD_RD_01 (bit 6) out of the internal
  344. * PHY registers
  345. */
  346. v = sw_r32(RTL839X_SDS12_13_XSG0 + offset + 0x80);
  347. if (!(v & (1 << 13)) && (v & (1 << 6)))
  348. phydev->speed = SPEED_1000;
  349. phydev->duplex = DUPLEX_FULL;
  350. }
  351. return err;
  352. }
  353. static int rtl8226_read_page(struct phy_device *phydev)
  354. {
  355. return __phy_read(phydev, RTL8XXX_PAGE_SELECT);
  356. }
  357. static int rtl8226_write_page(struct phy_device *phydev, int page)
  358. {
  359. return __phy_write(phydev, RTL8XXX_PAGE_SELECT, page);
  360. }
  361. static int rtl8226_read_status(struct phy_device *phydev)
  362. {
  363. int ret = 0;
  364. u32 val;
  365. /* TODO: ret = genphy_read_status(phydev);
  366. * if (ret < 0) {
  367. * pr_info("%s: genphy_read_status failed\n", __func__);
  368. * return ret;
  369. * }
  370. */
  371. /* Link status must be read twice */
  372. for (int i = 0; i < 2; i++)
  373. val = phy_read_mmd(phydev, MDIO_MMD_VEND2, 0xA402);
  374. phydev->link = val & BIT(2) ? 1 : 0;
  375. if (!phydev->link)
  376. goto out;
  377. /* Read duplex status */
  378. val = phy_read_mmd(phydev, MDIO_MMD_VEND2, 0xA434);
  379. if (val < 0)
  380. goto out;
  381. phydev->duplex = !!(val & BIT(3));
  382. /* Read speed */
  383. val = phy_read_mmd(phydev, MDIO_MMD_VEND2, 0xA434);
  384. switch (val & 0x0630) {
  385. case 0x0000:
  386. phydev->speed = SPEED_10;
  387. break;
  388. case 0x0010:
  389. phydev->speed = SPEED_100;
  390. break;
  391. case 0x0020:
  392. phydev->speed = SPEED_1000;
  393. break;
  394. case 0x0200:
  395. phydev->speed = SPEED_10000;
  396. break;
  397. case 0x0210:
  398. phydev->speed = SPEED_2500;
  399. break;
  400. case 0x0220:
  401. phydev->speed = SPEED_5000;
  402. break;
  403. default:
  404. break;
  405. }
  406. out:
  407. return ret;
  408. }
  409. static int rtl8226_advertise_aneg(struct phy_device *phydev)
  410. {
  411. int ret = 0;
  412. u32 v;
  413. pr_info("In %s\n", __func__);
  414. v = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_ADVERTISE);
  415. if (v < 0)
  416. goto out;
  417. v |= ADVERTISE_10HALF;
  418. v |= ADVERTISE_10FULL;
  419. v |= ADVERTISE_100HALF;
  420. v |= ADVERTISE_100FULL;
  421. ret = phy_write_mmd(phydev, MDIO_MMD_AN, MDIO_AN_ADVERTISE, v);
  422. /* Allow 1GBit */
  423. v = phy_read_mmd(phydev, MDIO_MMD_VEND2, 0xA412);
  424. if (v < 0)
  425. goto out;
  426. v |= ADVERTISE_1000FULL;
  427. ret = phy_write_mmd(phydev, MDIO_MMD_VEND2, 0xA412, v);
  428. if (ret < 0)
  429. goto out;
  430. /* Allow 2.5G */
  431. v = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_10GBT_CTRL);
  432. if (v < 0)
  433. goto out;
  434. v |= MDIO_AN_10GBT_CTRL_ADV2_5G;
  435. ret = phy_write_mmd(phydev, MDIO_MMD_AN, MDIO_AN_10GBT_CTRL, v);
  436. out:
  437. return ret;
  438. }
  439. static int rtl8226_config_aneg(struct phy_device *phydev)
  440. {
  441. int ret = 0;
  442. u32 v;
  443. pr_debug("In %s\n", __func__);
  444. if (phydev->autoneg == AUTONEG_ENABLE) {
  445. ret = rtl8226_advertise_aneg(phydev);
  446. if (ret)
  447. goto out;
  448. /* AutoNegotiationEnable */
  449. v = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_CTRL1);
  450. if (v < 0)
  451. goto out;
  452. v |= MDIO_AN_CTRL1_ENABLE; /* Enable AN */
  453. ret = phy_write_mmd(phydev, MDIO_MMD_AN, MDIO_CTRL1, v);
  454. if (ret < 0)
  455. goto out;
  456. /* RestartAutoNegotiation */
  457. v = phy_read_mmd(phydev, MDIO_MMD_VEND2, 0xA400);
  458. if (v < 0)
  459. goto out;
  460. v |= MDIO_AN_CTRL1_RESTART;
  461. ret = phy_write_mmd(phydev, MDIO_MMD_VEND2, 0xA400, v);
  462. }
  463. /* TODO: ret = __genphy_config_aneg(phydev, ret); */
  464. out:
  465. return ret;
  466. }
  467. static int rtl8226_get_eee(struct phy_device *phydev,
  468. struct ethtool_eee *e)
  469. {
  470. u32 val;
  471. int addr = phydev->mdio.addr;
  472. pr_debug("In %s, port %d, was enabled: %d\n", __func__, addr, e->eee_enabled);
  473. val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_ADV);
  474. if (e->eee_enabled) {
  475. e->eee_enabled = !!(val & MDIO_EEE_100TX);
  476. if (!e->eee_enabled) {
  477. val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_ADV2);
  478. e->eee_enabled = !!(val & MDIO_EEE_2_5GT);
  479. }
  480. }
  481. pr_debug("%s: enabled: %d\n", __func__, e->eee_enabled);
  482. return 0;
  483. }
  484. static int rtl8226_set_eee(struct phy_device *phydev, struct ethtool_eee *e)
  485. {
  486. int port = phydev->mdio.addr;
  487. u64 poll_state;
  488. bool an_enabled;
  489. u32 val;
  490. pr_info("In %s, port %d, enabled %d\n", __func__, port, e->eee_enabled);
  491. poll_state = disable_polling(port);
  492. /* Remember aneg state */
  493. val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_CTRL1);
  494. an_enabled = !!(val & MDIO_AN_CTRL1_ENABLE);
  495. /* Setup 100/1000MBit */
  496. val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_ADV);
  497. if (e->eee_enabled)
  498. val |= (MDIO_EEE_100TX | MDIO_EEE_1000T);
  499. else
  500. val &= (MDIO_EEE_100TX | MDIO_EEE_1000T);
  501. phy_write_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_ADV, val);
  502. /* Setup 2.5GBit */
  503. val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_ADV2);
  504. if (e->eee_enabled)
  505. val |= MDIO_EEE_2_5GT;
  506. else
  507. val &= MDIO_EEE_2_5GT;
  508. phy_write_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_ADV2, val);
  509. /* RestartAutoNegotiation */
  510. val = phy_read_mmd(phydev, MDIO_MMD_VEND2, 0xA400);
  511. val |= MDIO_AN_CTRL1_RESTART;
  512. phy_write_mmd(phydev, MDIO_MMD_VEND2, 0xA400, val);
  513. resume_polling(poll_state);
  514. return 0;
  515. }
  516. static struct fw_header *rtl838x_request_fw(struct phy_device *phydev,
  517. const struct firmware *fw,
  518. const char *name)
  519. {
  520. struct device *dev = &phydev->mdio.dev;
  521. int err;
  522. struct fw_header *h;
  523. uint32_t checksum, my_checksum;
  524. err = request_firmware(&fw, name, dev);
  525. if (err < 0)
  526. goto out;
  527. if (fw->size < sizeof(struct fw_header)) {
  528. pr_err("Firmware size too small.\n");
  529. err = -EINVAL;
  530. goto out;
  531. }
  532. h = (struct fw_header *) fw->data;
  533. pr_info("Firmware loaded. Size %d, magic: %08x\n", fw->size, h->magic);
  534. if (h->magic != 0x83808380) {
  535. pr_err("Wrong firmware file: MAGIC mismatch.\n");
  536. goto out;
  537. }
  538. checksum = h->checksum;
  539. h->checksum = 0;
  540. my_checksum = ~crc32(0xFFFFFFFFU, fw->data, fw->size);
  541. if (checksum != my_checksum) {
  542. pr_err("Firmware checksum mismatch.\n");
  543. err = -EINVAL;
  544. goto out;
  545. }
  546. h->checksum = checksum;
  547. return h;
  548. out:
  549. dev_err(dev, "Unable to load firmware %s (%d)\n", name, err);
  550. return NULL;
  551. }
  552. static void rtl821x_phy_setup_package_broadcast(struct phy_device *phydev, bool enable)
  553. {
  554. int mac = phydev->mdio.addr;
  555. /* select main page 0 */
  556. phy_write_paged(phydev, RTL83XX_PAGE_RAW, RTL8XXX_PAGE_SELECT, RTL8XXX_PAGE_MAIN);
  557. /* write to 0x8 to register 0x1d on main page 0 */
  558. phy_write_paged(phydev, RTL83XX_PAGE_RAW, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_INTERNAL);
  559. /* select page 0x266 */
  560. phy_write_paged(phydev, RTL83XX_PAGE_RAW, RTL8XXX_PAGE_SELECT, RTL821X_PAGE_PORT);
  561. /* set phy id and target broadcast bitmap in register 0x16 on page 0x266 */
  562. phy_write_paged(phydev, RTL83XX_PAGE_RAW, 0x16, (enable?0xff00:0x00) | mac);
  563. /* return to main page 0 */
  564. phy_write_paged(phydev, RTL83XX_PAGE_RAW, RTL8XXX_PAGE_SELECT, RTL8XXX_PAGE_MAIN);
  565. /* write to 0x0 to register 0x1d on main page 0 */
  566. phy_write_paged(phydev, RTL83XX_PAGE_RAW, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_AUTO);
  567. mdelay(1);
  568. }
  569. static int rtl8390_configure_generic(struct phy_device *phydev)
  570. {
  571. int mac = phydev->mdio.addr;
  572. u32 val, phy_id;
  573. val = phy_read(phydev, 2);
  574. phy_id = val << 16;
  575. val = phy_read(phydev, 3);
  576. phy_id |= val;
  577. pr_debug("Phy on MAC %d: %x\n", mac, phy_id);
  578. /* Read internal PHY ID */
  579. phy_write_paged(phydev, 31, 27, 0x0002);
  580. val = phy_read_paged(phydev, 31, 28);
  581. /* Internal RTL8218B, version 2 */
  582. phydev_info(phydev, "Detected unknown %x\n", val);
  583. return 0;
  584. }
  585. static int rtl8380_configure_int_rtl8218b(struct phy_device *phydev)
  586. {
  587. u32 val, phy_id;
  588. int mac = phydev->mdio.addr;
  589. struct fw_header *h;
  590. u32 *rtl838x_6275B_intPhy_perport;
  591. u32 *rtl8218b_6276B_hwEsd_perport;
  592. val = phy_read(phydev, 2);
  593. phy_id = val << 16;
  594. val = phy_read(phydev, 3);
  595. phy_id |= val;
  596. pr_debug("Phy on MAC %d: %x\n", mac, phy_id);
  597. /* Read internal PHY ID */
  598. phy_write_paged(phydev, 31, 27, 0x0002);
  599. val = phy_read_paged(phydev, 31, 28);
  600. if (val != 0x6275) {
  601. phydev_err(phydev, "Expected internal RTL8218B, found PHY-ID %x\n", val);
  602. return -1;
  603. }
  604. /* Internal RTL8218B, version 2 */
  605. phydev_info(phydev, "Detected internal RTL8218B\n");
  606. h = rtl838x_request_fw(phydev, &rtl838x_8380_fw, FIRMWARE_838X_8380_1);
  607. if (!h)
  608. return -1;
  609. if (h->phy != 0x83800000) {
  610. phydev_err(phydev, "Wrong firmware file: PHY mismatch.\n");
  611. return -1;
  612. }
  613. rtl838x_6275B_intPhy_perport = (void *)h + sizeof(struct fw_header) + h->parts[8].start;
  614. rtl8218b_6276B_hwEsd_perport = (void *)h + sizeof(struct fw_header) + h->parts[9].start;
  615. // Currently not used
  616. // if (sw_r32(RTL838X_DMY_REG31) == 0x1) {
  617. // int ipd_flag = 1;
  618. // }
  619. val = phy_read(phydev, MII_BMCR);
  620. if (val & BMCR_PDOWN)
  621. rtl8380_int_phy_on_off(phydev, true);
  622. else
  623. rtl8380_phy_reset(phydev);
  624. msleep(100);
  625. /* Ready PHY for patch */
  626. for (int p = 0; p < 8; p++) {
  627. phy_package_port_write_paged(phydev, p, RTL83XX_PAGE_RAW, RTL8XXX_PAGE_SELECT, RTL821X_PAGE_PATCH);
  628. phy_package_port_write_paged(phydev, p, RTL83XX_PAGE_RAW, 0x10, 0x0010);
  629. }
  630. msleep(500);
  631. for (int p = 0; p < 8; p++) {
  632. int i;
  633. for (i = 0; i < 100 ; i++) {
  634. val = phy_package_port_read_paged(phydev, p, RTL821X_PAGE_STATE, 0x10);
  635. if (val & 0x40)
  636. break;
  637. }
  638. if (i >= 100) {
  639. phydev_err(phydev,
  640. "ERROR: Port %d not ready for patch.\n",
  641. mac + p);
  642. return -1;
  643. }
  644. }
  645. for (int p = 0; p < 8; p++) {
  646. int i;
  647. i = 0;
  648. while (rtl838x_6275B_intPhy_perport[i * 2]) {
  649. phy_package_port_write_paged(phydev, p, RTL83XX_PAGE_RAW,
  650. rtl838x_6275B_intPhy_perport[i * 2],
  651. rtl838x_6275B_intPhy_perport[i * 2 + 1]);
  652. i++;
  653. }
  654. i = 0;
  655. while (rtl8218b_6276B_hwEsd_perport[i * 2]) {
  656. phy_package_port_write_paged(phydev, p, RTL83XX_PAGE_RAW,
  657. rtl8218b_6276B_hwEsd_perport[i * 2],
  658. rtl8218b_6276B_hwEsd_perport[i * 2 + 1]);
  659. i++;
  660. }
  661. }
  662. return 0;
  663. }
  664. static int rtl8380_configure_ext_rtl8218b(struct phy_device *phydev)
  665. {
  666. u32 val, ipd, phy_id;
  667. int mac = phydev->mdio.addr;
  668. struct fw_header *h;
  669. u32 *rtl8380_rtl8218b_perchip;
  670. u32 *rtl8218B_6276B_rtl8380_perport;
  671. u32 *rtl8380_rtl8218b_perport;
  672. if (soc_info.family == RTL8380_FAMILY_ID && mac != 0 && mac != 16) {
  673. phydev_err(phydev, "External RTL8218B must have PHY-IDs 0 or 16!\n");
  674. return -1;
  675. }
  676. val = phy_read(phydev, 2);
  677. phy_id = val << 16;
  678. val = phy_read(phydev, 3);
  679. phy_id |= val;
  680. pr_info("Phy on MAC %d: %x\n", mac, phy_id);
  681. /* Read internal PHY ID */
  682. phy_write_paged(phydev, 31, 27, 0x0002);
  683. val = phy_read_paged(phydev, 31, 28);
  684. if (val != 0x6276) {
  685. phydev_err(phydev, "Expected external RTL8218B, found PHY-ID %x\n", val);
  686. return -1;
  687. }
  688. phydev_info(phydev, "Detected external RTL8218B\n");
  689. h = rtl838x_request_fw(phydev, &rtl838x_8218b_fw, FIRMWARE_838X_8218b_1);
  690. if (!h)
  691. return -1;
  692. if (h->phy != 0x8218b000) {
  693. phydev_err(phydev, "Wrong firmware file: PHY mismatch.\n");
  694. return -1;
  695. }
  696. rtl8380_rtl8218b_perchip = (void *)h + sizeof(struct fw_header) + h->parts[0].start;
  697. rtl8218B_6276B_rtl8380_perport = (void *)h + sizeof(struct fw_header) + h->parts[1].start;
  698. rtl8380_rtl8218b_perport = (void *)h + sizeof(struct fw_header) + h->parts[2].start;
  699. val = phy_read(phydev, MII_BMCR);
  700. if (val & BMCR_PDOWN)
  701. rtl8380_int_phy_on_off(phydev, true);
  702. else
  703. rtl8380_phy_reset(phydev);
  704. msleep(100);
  705. /* Get Chip revision */
  706. phy_write_paged(phydev, RTL83XX_PAGE_RAW, RTL8XXX_PAGE_SELECT, RTL8XXX_PAGE_MAIN);
  707. phy_write_paged(phydev, RTL83XX_PAGE_RAW, 0x1b, 0x4);
  708. val = phy_read_paged(phydev, RTL83XX_PAGE_RAW, 0x1c);
  709. phydev_info(phydev, "Detected chip revision %04x\n", val);
  710. for (int i = 0; rtl8380_rtl8218b_perchip[i * 3] &&
  711. rtl8380_rtl8218b_perchip[i * 3 + 1]; i++) {
  712. phy_package_port_write_paged(phydev, rtl8380_rtl8218b_perchip[i * 3],
  713. RTL83XX_PAGE_RAW, rtl8380_rtl8218b_perchip[i * 3 + 1],
  714. rtl8380_rtl8218b_perchip[i * 3 + 2]);
  715. }
  716. /* Enable PHY */
  717. for (int i = 0; i < 8; i++) {
  718. phy_package_port_write_paged(phydev, i, RTL83XX_PAGE_RAW, RTL8XXX_PAGE_SELECT, RTL8XXX_PAGE_MAIN);
  719. phy_package_port_write_paged(phydev, i, RTL83XX_PAGE_RAW, 0x00, 0x1140);
  720. }
  721. mdelay(100);
  722. /* Request patch */
  723. for (int i = 0; i < 8; i++) {
  724. phy_package_port_write_paged(phydev, i, RTL83XX_PAGE_RAW, RTL8XXX_PAGE_SELECT, RTL821X_PAGE_PATCH);
  725. phy_package_port_write_paged(phydev, i, RTL83XX_PAGE_RAW, 0x10, 0x0010);
  726. }
  727. mdelay(300);
  728. /* Verify patch readiness */
  729. for (int i = 0; i < 8; i++) {
  730. int l;
  731. for (l = 0; l < 100; l++) {
  732. val = phy_package_port_read_paged(phydev, i, RTL821X_PAGE_STATE, 0x10);
  733. if (val & 0x40)
  734. break;
  735. }
  736. if (l >= 100) {
  737. phydev_err(phydev, "Could not patch PHY\n");
  738. return -1;
  739. }
  740. }
  741. /* Use Broadcast ID method for patching */
  742. rtl821x_phy_setup_package_broadcast(phydev, true);
  743. phy_write_paged(phydev, RTL83XX_PAGE_RAW, 30, 8);
  744. phy_write_paged(phydev, 0x26e, 17, 0xb);
  745. phy_write_paged(phydev, 0x26e, 16, 0x2);
  746. mdelay(1);
  747. ipd = phy_read_paged(phydev, 0x26e, 19);
  748. phy_write_paged(phydev, 0, 30, 0);
  749. ipd = (ipd >> 4) & 0xf; /* unused ? */
  750. for (int i = 0; rtl8218B_6276B_rtl8380_perport[i * 2]; i++) {
  751. phy_write_paged(phydev, RTL83XX_PAGE_RAW, rtl8218B_6276B_rtl8380_perport[i * 2],
  752. rtl8218B_6276B_rtl8380_perport[i * 2 + 1]);
  753. }
  754. /* Disable broadcast ID */
  755. rtl821x_phy_setup_package_broadcast(phydev, false);
  756. return 0;
  757. }
  758. static int rtl8218b_ext_match_phy_device(struct phy_device *phydev)
  759. {
  760. int addr = phydev->mdio.addr;
  761. /* Both the RTL8214FC and the external RTL8218B have the same
  762. * PHY ID. On the RTL838x, the RTL8218B can only be attached_dev
  763. * at PHY IDs 0-7, while the RTL8214FC must be attached via
  764. * the pair of SGMII/1000Base-X with higher PHY-IDs
  765. */
  766. if (soc_info.family == RTL8380_FAMILY_ID)
  767. return phydev->phy_id == PHY_ID_RTL8218B_E && addr < 8;
  768. else
  769. return phydev->phy_id == PHY_ID_RTL8218B_E;
  770. }
  771. static bool rtl8214fc_media_is_fibre(struct phy_device *phydev)
  772. {
  773. int mac = phydev->mdio.addr;
  774. static int reg[] = {16, 19, 20, 21};
  775. u32 val;
  776. phy_package_write_paged(phydev, RTL83XX_PAGE_RAW, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_INTERNAL);
  777. val = phy_package_read_paged(phydev, RTL821X_PAGE_PORT, reg[mac % 4]);
  778. phy_package_write_paged(phydev, RTL83XX_PAGE_RAW, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_AUTO);
  779. if (val & BMCR_PDOWN)
  780. return false;
  781. return true;
  782. }
  783. static void rtl8214fc_power_set(struct phy_device *phydev, int port, bool on)
  784. {
  785. char *state = on ? "on" : "off";
  786. if (port == PORT_FIBRE) {
  787. pr_info("%s: Powering %s FIBRE (port %d)\n", __func__, state, phydev->mdio.addr);
  788. phy_write_paged(phydev, RTL83XX_PAGE_RAW, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_FIBRE);
  789. } else {
  790. pr_info("%s: Powering %s COPPER (port %d)\n", __func__, state, phydev->mdio.addr);
  791. phy_write_paged(phydev, RTL83XX_PAGE_RAW, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_COPPER);
  792. }
  793. if (on) {
  794. phy_modify_paged(phydev, RTL821X_PAGE_POWER, 0x10, BMCR_PDOWN, 0);
  795. } else {
  796. phy_modify_paged(phydev, RTL821X_PAGE_POWER, 0x10, 0, BMCR_PDOWN);
  797. }
  798. phy_write_paged(phydev, RTL83XX_PAGE_RAW, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_AUTO);
  799. }
  800. static int rtl8214fc_suspend(struct phy_device *phydev)
  801. {
  802. rtl8214fc_power_set(phydev, PORT_MII, false);
  803. rtl8214fc_power_set(phydev, PORT_FIBRE, false);
  804. return 0;
  805. }
  806. static int rtl8214fc_resume(struct phy_device *phydev)
  807. {
  808. if (rtl8214fc_media_is_fibre(phydev)) {
  809. rtl8214fc_power_set(phydev, PORT_MII, false);
  810. rtl8214fc_power_set(phydev, PORT_FIBRE, true);
  811. } else {
  812. rtl8214fc_power_set(phydev, PORT_FIBRE, false);
  813. rtl8214fc_power_set(phydev, PORT_MII, true);
  814. }
  815. return 0;
  816. }
  817. static void rtl8214fc_media_set(struct phy_device *phydev, bool set_fibre)
  818. {
  819. int mac = phydev->mdio.addr;
  820. static int reg[] = {16, 19, 20, 21};
  821. int val;
  822. pr_info("%s: port %d, set_fibre: %d\n", __func__, mac, set_fibre);
  823. phy_package_write_paged(phydev, RTL83XX_PAGE_RAW, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_INTERNAL);
  824. val = phy_package_read_paged(phydev, RTL821X_PAGE_PORT, reg[mac % 4]);
  825. val |= BIT(10);
  826. if (set_fibre) {
  827. val &= ~BMCR_PDOWN;
  828. } else {
  829. val |= BMCR_PDOWN;
  830. }
  831. phy_package_write_paged(phydev, RTL83XX_PAGE_RAW, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_INTERNAL);
  832. phy_package_write_paged(phydev, RTL821X_PAGE_PORT, reg[mac % 4], val);
  833. phy_package_write_paged(phydev, RTL83XX_PAGE_RAW, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_AUTO);
  834. if (!phydev->suspended) {
  835. if (set_fibre) {
  836. rtl8214fc_power_set(phydev, PORT_MII, false);
  837. rtl8214fc_power_set(phydev, PORT_FIBRE, true);
  838. } else {
  839. rtl8214fc_power_set(phydev, PORT_FIBRE, false);
  840. rtl8214fc_power_set(phydev, PORT_MII, true);
  841. }
  842. }
  843. }
  844. static int rtl8214fc_set_port(struct phy_device *phydev, int port)
  845. {
  846. bool is_fibre = (port == PORT_FIBRE ? true : false);
  847. int addr = phydev->mdio.addr;
  848. pr_debug("%s port %d to %d\n", __func__, addr, port);
  849. rtl8214fc_media_set(phydev, is_fibre);
  850. return 0;
  851. }
  852. static int rtl8214fc_get_port(struct phy_device *phydev)
  853. {
  854. int addr = phydev->mdio.addr;
  855. pr_debug("%s: port %d\n", __func__, addr);
  856. if (rtl8214fc_media_is_fibre(phydev))
  857. return PORT_FIBRE;
  858. return PORT_MII;
  859. }
  860. /* Enable EEE on the RTL8218B PHYs
  861. * The method used is not the preferred way (which would be based on the MAC-EEE state,
  862. * but the only way that works since the kernel first enables EEE in the MAC
  863. * and then sets up the PHY. The MAC-based approach would require the oppsite.
  864. */
  865. void rtl8218d_eee_set(struct phy_device *phydev, bool enable)
  866. {
  867. u32 val;
  868. bool an_enabled;
  869. pr_debug("In %s %d, enable %d\n", __func__, phydev->mdio.addr, enable);
  870. /* Set GPHY page to copper */
  871. phy_write_paged(phydev, RTL821X_PAGE_GPHY, RTL821XEXT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_COPPER);
  872. val = phy_read(phydev, MII_BMCR);
  873. an_enabled = val & BMCR_ANENABLE;
  874. val = phy_read_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_ADV);
  875. val |= MDIO_EEE_1000T | MDIO_EEE_100TX;
  876. phy_write_mmd(phydev, MDIO_MMD_AN, MDIO_AN_EEE_ADV, enable ? (MDIO_EEE_100TX | MDIO_EEE_1000T) : 0);
  877. /* 500M EEE ability */
  878. val = phy_read_paged(phydev, RTL821X_PAGE_GPHY, 20);
  879. if (enable)
  880. val |= BIT(7);
  881. else
  882. val &= ~BIT(7);
  883. phy_write_paged(phydev, RTL821X_PAGE_GPHY, 20, val);
  884. /* Restart AN if enabled */
  885. if (an_enabled) {
  886. val = phy_read(phydev, MII_BMCR);
  887. val |= BMCR_ANRESTART;
  888. phy_write(phydev, MII_BMCR, val);
  889. }
  890. /* GPHY page back to auto */
  891. phy_write_paged(phydev, RTL821X_PAGE_GPHY, RTL821XEXT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_AUTO);
  892. }
  893. static int rtl8218b_get_eee(struct phy_device *phydev,
  894. struct ethtool_eee *e)
  895. {
  896. u32 val;
  897. int addr = phydev->mdio.addr;
  898. pr_debug("In %s, port %d, was enabled: %d\n", __func__, addr, e->eee_enabled);
  899. /* Set GPHY page to copper */
  900. phy_write_paged(phydev, RTL821X_PAGE_GPHY, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_COPPER);
  901. val = phy_read_paged(phydev, 7, MDIO_AN_EEE_ADV);
  902. if (e->eee_enabled) {
  903. /* Verify vs MAC-based EEE */
  904. e->eee_enabled = !!(val & BIT(7));
  905. if (!e->eee_enabled) {
  906. val = phy_read_paged(phydev, RTL821X_PAGE_MAC, 25);
  907. e->eee_enabled = !!(val & BIT(4));
  908. }
  909. }
  910. pr_debug("%s: enabled: %d\n", __func__, e->eee_enabled);
  911. /* GPHY page to auto */
  912. phy_write_paged(phydev, RTL821X_PAGE_GPHY, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_AUTO);
  913. return 0;
  914. }
  915. static int rtl8218d_get_eee(struct phy_device *phydev,
  916. struct ethtool_eee *e)
  917. {
  918. u32 val;
  919. int addr = phydev->mdio.addr;
  920. pr_debug("In %s, port %d, was enabled: %d\n", __func__, addr, e->eee_enabled);
  921. /* Set GPHY page to copper */
  922. phy_write_paged(phydev, RTL821X_PAGE_GPHY, RTL821XEXT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_COPPER);
  923. val = phy_read_paged(phydev, 7, MDIO_AN_EEE_ADV);
  924. if (e->eee_enabled)
  925. e->eee_enabled = !!(val & BIT(7));
  926. pr_debug("%s: enabled: %d\n", __func__, e->eee_enabled);
  927. /* GPHY page to auto */
  928. phy_write_paged(phydev, RTL821X_PAGE_GPHY, RTL821XEXT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_AUTO);
  929. return 0;
  930. }
  931. static int rtl8214fc_set_eee(struct phy_device *phydev,
  932. struct ethtool_eee *e)
  933. {
  934. u32 poll_state;
  935. int port = phydev->mdio.addr;
  936. bool an_enabled;
  937. u32 val;
  938. pr_debug("In %s port %d, enabled %d\n", __func__, port, e->eee_enabled);
  939. if (rtl8214fc_media_is_fibre(phydev)) {
  940. netdev_err(phydev->attached_dev, "Port %d configured for FIBRE", port);
  941. return -ENOTSUPP;
  942. }
  943. poll_state = disable_polling(port);
  944. /* Set GPHY page to copper */
  945. phy_write_paged(phydev, RTL821X_PAGE_GPHY, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_COPPER);
  946. /* Get auto-negotiation status */
  947. val = phy_read(phydev, MII_BMCR);
  948. an_enabled = val & BMCR_ANENABLE;
  949. pr_info("%s: aneg: %d\n", __func__, an_enabled);
  950. val = phy_read_paged(phydev, RTL821X_PAGE_MAC, 25);
  951. val &= ~BIT(5); /* Use MAC-based EEE */
  952. phy_write_paged(phydev, RTL821X_PAGE_MAC, 25, val);
  953. /* Enable 100M (bit 1) / 1000M (bit 2) EEE */
  954. phy_write_paged(phydev, 7, MDIO_AN_EEE_ADV, e->eee_enabled ? (MDIO_EEE_100TX | MDIO_EEE_1000T) : 0);
  955. /* 500M EEE ability */
  956. val = phy_read_paged(phydev, RTL821X_PAGE_GPHY, 20);
  957. if (e->eee_enabled)
  958. val |= BIT(7);
  959. else
  960. val &= ~BIT(7);
  961. phy_write_paged(phydev, RTL821X_PAGE_GPHY, 20, val);
  962. /* Restart AN if enabled */
  963. if (an_enabled) {
  964. pr_info("%s: doing aneg\n", __func__);
  965. val = phy_read(phydev, MII_BMCR);
  966. val |= BMCR_ANRESTART;
  967. phy_write(phydev, MII_BMCR, val);
  968. }
  969. /* GPHY page back to auto */
  970. phy_write_paged(phydev, RTL821X_PAGE_GPHY, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_AUTO);
  971. resume_polling(poll_state);
  972. return 0;
  973. }
  974. static int rtl8214fc_get_eee(struct phy_device *phydev,
  975. struct ethtool_eee *e)
  976. {
  977. int addr = phydev->mdio.addr;
  978. pr_debug("In %s port %d, enabled %d\n", __func__, addr, e->eee_enabled);
  979. if (rtl8214fc_media_is_fibre(phydev)) {
  980. netdev_err(phydev->attached_dev, "Port %d configured for FIBRE", addr);
  981. return -ENOTSUPP;
  982. }
  983. return rtl8218b_get_eee(phydev, e);
  984. }
  985. static int rtl8218b_set_eee(struct phy_device *phydev, struct ethtool_eee *e)
  986. {
  987. int port = phydev->mdio.addr;
  988. u64 poll_state;
  989. u32 val;
  990. bool an_enabled;
  991. pr_info("In %s, port %d, enabled %d\n", __func__, port, e->eee_enabled);
  992. poll_state = disable_polling(port);
  993. /* Set GPHY page to copper */
  994. phy_write(phydev, RTL821XEXT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_COPPER);
  995. val = phy_read(phydev, MII_BMCR);
  996. an_enabled = val & BMCR_ANENABLE;
  997. if (e->eee_enabled) {
  998. /* 100/1000M EEE Capability */
  999. phy_write(phydev, 13, 0x0007);
  1000. phy_write(phydev, 14, 0x003C);
  1001. phy_write(phydev, 13, 0x4007);
  1002. phy_write(phydev, 14, 0x0006);
  1003. val = phy_read_paged(phydev, RTL821X_PAGE_MAC, 25);
  1004. val |= BIT(4);
  1005. phy_write_paged(phydev, RTL821X_PAGE_MAC, 25, val);
  1006. } else {
  1007. /* 100/1000M EEE Capability */
  1008. phy_write(phydev, 13, 0x0007);
  1009. phy_write(phydev, 14, 0x003C);
  1010. phy_write(phydev, 13, 0x0007);
  1011. phy_write(phydev, 14, 0x0000);
  1012. val = phy_read_paged(phydev, RTL821X_PAGE_MAC, 25);
  1013. val &= ~BIT(4);
  1014. phy_write_paged(phydev, RTL821X_PAGE_MAC, 25, val);
  1015. }
  1016. /* Restart AN if enabled */
  1017. if (an_enabled) {
  1018. val = phy_read(phydev, MII_BMCR);
  1019. val |= BMCR_ANRESTART;
  1020. phy_write(phydev, MII_BMCR, val);
  1021. }
  1022. /* GPHY page back to auto */
  1023. phy_write_paged(phydev, RTL821X_PAGE_GPHY, RTL821XEXT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_AUTO);
  1024. pr_info("%s done\n", __func__);
  1025. resume_polling(poll_state);
  1026. return 0;
  1027. }
  1028. static int rtl8218d_set_eee(struct phy_device *phydev, struct ethtool_eee *e)
  1029. {
  1030. int addr = phydev->mdio.addr;
  1031. u64 poll_state;
  1032. pr_info("In %s, port %d, enabled %d\n", __func__, addr, e->eee_enabled);
  1033. poll_state = disable_polling(addr);
  1034. rtl8218d_eee_set(phydev, (bool) e->eee_enabled);
  1035. resume_polling(poll_state);
  1036. return 0;
  1037. }
  1038. static int rtl8214c_match_phy_device(struct phy_device *phydev)
  1039. {
  1040. return phydev->phy_id == PHY_ID_RTL8214C;
  1041. }
  1042. static int rtl8380_configure_rtl8214c(struct phy_device *phydev)
  1043. {
  1044. u32 phy_id, val;
  1045. int mac = phydev->mdio.addr;
  1046. val = phy_read(phydev, 2);
  1047. phy_id = val << 16;
  1048. val = phy_read(phydev, 3);
  1049. phy_id |= val;
  1050. pr_debug("Phy on MAC %d: %x\n", mac, phy_id);
  1051. phydev_info(phydev, "Detected external RTL8214C\n");
  1052. /* GPHY auto conf */
  1053. phy_write_paged(phydev, RTL821X_PAGE_GPHY, RTL821XINT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_AUTO);
  1054. return 0;
  1055. }
  1056. static int rtl8380_configure_rtl8214fc(struct phy_device *phydev)
  1057. {
  1058. int mac = phydev->mdio.addr;
  1059. struct fw_header *h;
  1060. u32 *rtl8380_rtl8214fc_perchip;
  1061. u32 *rtl8380_rtl8214fc_perport;
  1062. u32 phy_id;
  1063. u32 val;
  1064. val = phy_read(phydev, 2);
  1065. phy_id = val << 16;
  1066. val = phy_read(phydev, 3);
  1067. phy_id |= val;
  1068. pr_debug("Phy on MAC %d: %x\n", mac, phy_id);
  1069. /* Read internal PHY id */
  1070. phy_write_paged(phydev, 0, RTL821XEXT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_COPPER);
  1071. phy_write_paged(phydev, 0x1f, 0x1b, 0x0002);
  1072. val = phy_read_paged(phydev, 0x1f, 0x1c);
  1073. if (val != 0x6276) {
  1074. phydev_err(phydev, "Expected external RTL8214FC, found PHY-ID %x\n", val);
  1075. return -1;
  1076. }
  1077. phydev_info(phydev, "Detected external RTL8214FC\n");
  1078. h = rtl838x_request_fw(phydev, &rtl838x_8214fc_fw, FIRMWARE_838X_8214FC_1);
  1079. if (!h)
  1080. return -1;
  1081. if (h->phy != 0x8214fc00) {
  1082. phydev_err(phydev, "Wrong firmware file: PHY mismatch.\n");
  1083. return -1;
  1084. }
  1085. rtl8380_rtl8214fc_perchip = (void *)h + sizeof(struct fw_header) + h->parts[0].start;
  1086. rtl8380_rtl8214fc_perport = (void *)h + sizeof(struct fw_header) + h->parts[1].start;
  1087. /* detect phy version */
  1088. phy_write_paged(phydev, RTL83XX_PAGE_RAW, 27, 0x0004);
  1089. val = phy_read_paged(phydev, RTL83XX_PAGE_RAW, 28);
  1090. val = phy_read(phydev, 16);
  1091. if (val & BMCR_PDOWN)
  1092. rtl8380_rtl8214fc_on_off(phydev, true);
  1093. else
  1094. rtl8380_phy_reset(phydev);
  1095. msleep(100);
  1096. phy_write_paged(phydev, 0, RTL821XEXT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_COPPER);
  1097. for (int i = 0; rtl8380_rtl8214fc_perchip[i * 3] &&
  1098. rtl8380_rtl8214fc_perchip[i * 3 + 1]; i++) {
  1099. u32 page = 0;
  1100. if (rtl8380_rtl8214fc_perchip[i * 3 + 1] == 0x1f)
  1101. page = rtl8380_rtl8214fc_perchip[i * 3 + 2];
  1102. if (rtl8380_rtl8214fc_perchip[i * 3 + 1] == 0x13 && page == 0x260) {
  1103. val = phy_read_paged(phydev, 0x260, 13);
  1104. val = (val & 0x1f00) | (rtl8380_rtl8214fc_perchip[i * 3 + 2] & 0xe0ff);
  1105. phy_write_paged(phydev, RTL83XX_PAGE_RAW,
  1106. rtl8380_rtl8214fc_perchip[i * 3 + 1], val);
  1107. } else {
  1108. phy_write_paged(phydev, RTL83XX_PAGE_RAW,
  1109. rtl8380_rtl8214fc_perchip[i * 3 + 1],
  1110. rtl8380_rtl8214fc_perchip[i * 3 + 2]);
  1111. }
  1112. }
  1113. /* Force copper medium */
  1114. for (int i = 0; i < 4; i++) {
  1115. phy_package_port_write_paged(phydev, i, RTL83XX_PAGE_RAW, RTL8XXX_PAGE_SELECT, RTL8XXX_PAGE_MAIN);
  1116. phy_package_port_write_paged(phydev, i, RTL83XX_PAGE_RAW, RTL821XEXT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_COPPER);
  1117. }
  1118. /* Enable PHY */
  1119. for (int i = 0; i < 4; i++) {
  1120. phy_package_port_write_paged(phydev, i, RTL83XX_PAGE_RAW, RTL8XXX_PAGE_SELECT, RTL8XXX_PAGE_MAIN);
  1121. phy_package_port_write_paged(phydev, i, RTL83XX_PAGE_RAW, 0x00, 0x1140);
  1122. }
  1123. mdelay(100);
  1124. /* Disable Autosensing */
  1125. for (int i = 0; i < 4; i++) {
  1126. int l;
  1127. for (l = 0; l < 100; l++) {
  1128. val = phy_package_port_read_paged(phydev, i, RTL821X_PAGE_GPHY, 0x10);
  1129. if ((val & 0x7) >= 3)
  1130. break;
  1131. }
  1132. if (l >= 100) {
  1133. phydev_err(phydev, "Could not disable autosensing\n");
  1134. return -1;
  1135. }
  1136. }
  1137. /* Request patch */
  1138. for (int i = 0; i < 4; i++) {
  1139. phy_package_port_write_paged(phydev, i, RTL83XX_PAGE_RAW, RTL8XXX_PAGE_SELECT, RTL821X_PAGE_PATCH);
  1140. phy_package_port_write_paged(phydev, i, RTL83XX_PAGE_RAW, 0x10, 0x0010);
  1141. }
  1142. mdelay(300);
  1143. /* Verify patch readiness */
  1144. for (int i = 0; i < 4; i++) {
  1145. int l;
  1146. for (l = 0; l < 100; l++) {
  1147. val = phy_package_port_read_paged(phydev, i, RTL821X_PAGE_STATE, 0x10);
  1148. if (val & 0x40)
  1149. break;
  1150. }
  1151. if (l >= 100) {
  1152. phydev_err(phydev, "Could not patch PHY\n");
  1153. return -1;
  1154. }
  1155. }
  1156. /* Use Broadcast ID method for patching */
  1157. rtl821x_phy_setup_package_broadcast(phydev, true);
  1158. for (int i = 0; rtl8380_rtl8214fc_perport[i * 2]; i++) {
  1159. phy_write_paged(phydev, RTL83XX_PAGE_RAW, rtl8380_rtl8214fc_perport[i * 2],
  1160. rtl8380_rtl8214fc_perport[i * 2 + 1]);
  1161. }
  1162. /* Disable broadcast ID */
  1163. rtl821x_phy_setup_package_broadcast(phydev, false);
  1164. /* Auto medium selection */
  1165. for (int i = 0; i < 4; i++) {
  1166. phy_write_paged(phydev, RTL83XX_PAGE_RAW, RTL8XXX_PAGE_SELECT, RTL8XXX_PAGE_MAIN);
  1167. phy_write_paged(phydev, RTL83XX_PAGE_RAW, RTL821XEXT_MEDIA_PAGE_SELECT, RTL821X_MEDIA_PAGE_AUTO);
  1168. }
  1169. return 0;
  1170. }
  1171. static int rtl8214fc_match_phy_device(struct phy_device *phydev)
  1172. {
  1173. int addr = phydev->mdio.addr;
  1174. return phydev->phy_id == PHY_ID_RTL8214FC && addr >= 24;
  1175. }
  1176. static int rtl8380_configure_serdes(struct phy_device *phydev)
  1177. {
  1178. u32 v;
  1179. u32 sds_conf_value;
  1180. int i;
  1181. struct fw_header *h;
  1182. u32 *rtl8380_sds_take_reset;
  1183. u32 *rtl8380_sds_common;
  1184. u32 *rtl8380_sds01_qsgmii_6275b;
  1185. u32 *rtl8380_sds23_qsgmii_6275b;
  1186. u32 *rtl8380_sds4_fiber_6275b;
  1187. u32 *rtl8380_sds5_fiber_6275b;
  1188. u32 *rtl8380_sds_reset;
  1189. u32 *rtl8380_sds_release_reset;
  1190. phydev_info(phydev, "Detected internal RTL8380 SERDES\n");
  1191. h = rtl838x_request_fw(phydev, &rtl838x_8218b_fw, FIRMWARE_838X_8380_1);
  1192. if (!h)
  1193. return -1;
  1194. if (h->magic != 0x83808380) {
  1195. phydev_err(phydev, "Wrong firmware file: magic number mismatch.\n");
  1196. return -1;
  1197. }
  1198. rtl8380_sds_take_reset = (void *)h + sizeof(struct fw_header) + h->parts[0].start;
  1199. rtl8380_sds_common = (void *)h + sizeof(struct fw_header) + h->parts[1].start;
  1200. rtl8380_sds01_qsgmii_6275b = (void *)h + sizeof(struct fw_header) + h->parts[2].start;
  1201. rtl8380_sds23_qsgmii_6275b = (void *)h + sizeof(struct fw_header) + h->parts[3].start;
  1202. rtl8380_sds4_fiber_6275b = (void *)h + sizeof(struct fw_header) + h->parts[4].start;
  1203. rtl8380_sds5_fiber_6275b = (void *)h + sizeof(struct fw_header) + h->parts[5].start;
  1204. rtl8380_sds_reset = (void *)h + sizeof(struct fw_header) + h->parts[6].start;
  1205. rtl8380_sds_release_reset = (void *)h + sizeof(struct fw_header) + h->parts[7].start;
  1206. /* Back up serdes power off value */
  1207. sds_conf_value = sw_r32(RTL838X_SDS_CFG_REG);
  1208. pr_info("SDS power down value: %x\n", sds_conf_value);
  1209. /* take serdes into reset */
  1210. i = 0;
  1211. while (rtl8380_sds_take_reset[2 * i]) {
  1212. sw_w32(rtl8380_sds_take_reset[2 * i + 1], rtl8380_sds_take_reset[2 * i]);
  1213. i++;
  1214. udelay(1000);
  1215. }
  1216. /* apply common serdes patch */
  1217. i = 0;
  1218. while (rtl8380_sds_common[2 * i]) {
  1219. sw_w32(rtl8380_sds_common[2 * i + 1], rtl8380_sds_common[2 * i]);
  1220. i++;
  1221. udelay(1000);
  1222. }
  1223. /* internal R/W enable */
  1224. sw_w32(3, RTL838X_INT_RW_CTRL);
  1225. /* SerDes ports 4 and 5 are FIBRE ports */
  1226. sw_w32_mask(0x7 | 0x38, 1 | (1 << 3), RTL838X_INT_MODE_CTRL);
  1227. /* SerDes module settings, SerDes 0-3 are QSGMII */
  1228. v = 0x6 << 25 | 0x6 << 20 | 0x6 << 15 | 0x6 << 10;
  1229. /* SerDes 4 and 5 are 1000BX FIBRE */
  1230. v |= 0x4 << 5 | 0x4;
  1231. sw_w32(v, RTL838X_SDS_MODE_SEL);
  1232. pr_info("PLL control register: %x\n", sw_r32(RTL838X_PLL_CML_CTRL));
  1233. sw_w32_mask(0xfffffff0, 0xaaaaaaaf & 0xf, RTL838X_PLL_CML_CTRL);
  1234. i = 0;
  1235. while (rtl8380_sds01_qsgmii_6275b[2 * i]) {
  1236. sw_w32(rtl8380_sds01_qsgmii_6275b[2 * i + 1],
  1237. rtl8380_sds01_qsgmii_6275b[2 * i]);
  1238. i++;
  1239. }
  1240. i = 0;
  1241. while (rtl8380_sds23_qsgmii_6275b[2 * i]) {
  1242. sw_w32(rtl8380_sds23_qsgmii_6275b[2 * i + 1], rtl8380_sds23_qsgmii_6275b[2 * i]);
  1243. i++;
  1244. }
  1245. i = 0;
  1246. while (rtl8380_sds4_fiber_6275b[2 * i]) {
  1247. sw_w32(rtl8380_sds4_fiber_6275b[2 * i + 1], rtl8380_sds4_fiber_6275b[2 * i]);
  1248. i++;
  1249. }
  1250. i = 0;
  1251. while (rtl8380_sds5_fiber_6275b[2 * i]) {
  1252. sw_w32(rtl8380_sds5_fiber_6275b[2 * i + 1], rtl8380_sds5_fiber_6275b[2 * i]);
  1253. i++;
  1254. }
  1255. i = 0;
  1256. while (rtl8380_sds_reset[2 * i]) {
  1257. sw_w32(rtl8380_sds_reset[2 * i + 1], rtl8380_sds_reset[2 * i]);
  1258. i++;
  1259. }
  1260. i = 0;
  1261. while (rtl8380_sds_release_reset[2 * i]) {
  1262. sw_w32(rtl8380_sds_release_reset[2 * i + 1], rtl8380_sds_release_reset[2 * i]);
  1263. i++;
  1264. }
  1265. pr_info("SDS power down value now: %x\n", sw_r32(RTL838X_SDS_CFG_REG));
  1266. sw_w32(sds_conf_value, RTL838X_SDS_CFG_REG);
  1267. pr_info("Configuration of SERDES done\n");
  1268. return 0;
  1269. }
  1270. static int rtl8390_configure_serdes(struct phy_device *phydev)
  1271. {
  1272. phydev_info(phydev, "Detected internal RTL8390 SERDES\n");
  1273. /* In autoneg state, force link, set SR4_CFG_EN_LINK_FIB1G */
  1274. sw_w32_mask(0, 1 << 18, RTL839X_SDS12_13_XSG0 + 0x0a);
  1275. /* Disable EEE: Clear FRE16_EEE_RSG_FIB1G, FRE16_EEE_STD_FIB1G,
  1276. * FRE16_C1_PWRSAV_EN_FIB1G, FRE16_C2_PWRSAV_EN_FIB1G
  1277. * and FRE16_EEE_QUIET_FIB1G
  1278. */
  1279. sw_w32_mask(0x1f << 10, 0, RTL839X_SDS12_13_XSG0 + 0xe0);
  1280. return 0;
  1281. }
  1282. void rtl9300_sds_field_w(int sds, u32 page, u32 reg, int end_bit, int start_bit, u32 v)
  1283. {
  1284. int l = end_bit - start_bit + 1;
  1285. u32 data = v;
  1286. if (l < 32) {
  1287. u32 mask = BIT(l) - 1;
  1288. data = rtl930x_read_sds_phy(sds, page, reg);
  1289. data &= ~(mask << start_bit);
  1290. data |= (v & mask) << start_bit;
  1291. }
  1292. rtl930x_write_sds_phy(sds, page, reg, data);
  1293. }
  1294. u32 rtl9300_sds_field_r(int sds, u32 page, u32 reg, int end_bit, int start_bit)
  1295. {
  1296. int l = end_bit - start_bit + 1;
  1297. u32 v = rtl930x_read_sds_phy(sds, page, reg);
  1298. if (l >= 32)
  1299. return v;
  1300. return (v >> start_bit) & (BIT(l) - 1);
  1301. }
  1302. /* Read the link and speed status of the internal SerDes of the RTL9300
  1303. */
  1304. static int rtl9300_read_status(struct phy_device *phydev)
  1305. {
  1306. struct device *dev = &phydev->mdio.dev;
  1307. int phy_addr = phydev->mdio.addr;
  1308. struct device_node *dn;
  1309. u32 sds_num = 0, status, latch_status, mode;
  1310. if (dev->of_node) {
  1311. dn = dev->of_node;
  1312. if (of_property_read_u32(dn, "sds", &sds_num))
  1313. sds_num = -1;
  1314. pr_info("%s: Port %d, SerDes is %d\n", __func__, phy_addr, sds_num);
  1315. } else {
  1316. dev_err(dev, "No DT node.\n");
  1317. return -EINVAL;
  1318. }
  1319. if (sds_num < 0)
  1320. return 0;
  1321. mode = rtl9300_sds_mode_get(sds_num);
  1322. pr_info("%s got SDS mode %02x\n", __func__, mode);
  1323. if (mode == RTL930X_SDS_OFF)
  1324. mode = rtl9300_sds_field_r(sds_num, 0x1f, 9, 11, 7);
  1325. if (mode == RTL930X_SDS_MODE_10GBASER) { /* 10GR mode */
  1326. status = rtl9300_sds_field_r(sds_num, 0x5, 0, 12, 12);
  1327. latch_status = rtl9300_sds_field_r(sds_num, 0x4, 1, 2, 2);
  1328. status |= rtl9300_sds_field_r(sds_num, 0x5, 0, 12, 12);
  1329. latch_status |= rtl9300_sds_field_r(sds_num, 0x4, 1, 2, 2);
  1330. } else {
  1331. status = rtl9300_sds_field_r(sds_num, 0x1, 29, 8, 0);
  1332. latch_status = rtl9300_sds_field_r(sds_num, 0x1, 30, 8, 0);
  1333. status |= rtl9300_sds_field_r(sds_num, 0x1, 29, 8, 0);
  1334. latch_status |= rtl9300_sds_field_r(sds_num, 0x1, 30, 8, 0);
  1335. }
  1336. pr_info("%s link status: status: %d, latch %d\n", __func__, status, latch_status);
  1337. if (latch_status) {
  1338. phydev->link = true;
  1339. if (mode == RTL930X_SDS_MODE_10GBASER) {
  1340. phydev->speed = SPEED_10000;
  1341. phydev->interface = PHY_INTERFACE_MODE_10GBASER;
  1342. } else {
  1343. phydev->speed = SPEED_1000;
  1344. phydev->interface = PHY_INTERFACE_MODE_1000BASEX;
  1345. }
  1346. phydev->duplex = DUPLEX_FULL;
  1347. }
  1348. return 0;
  1349. }
  1350. void rtl930x_sds_rx_rst(int sds_num, phy_interface_t phy_if)
  1351. {
  1352. int page = 0x2e; /* 10GR and USXGMII */
  1353. if (phy_if == PHY_INTERFACE_MODE_1000BASEX)
  1354. page = 0x24;
  1355. rtl9300_sds_field_w(sds_num, page, 0x15, 4, 4, 0x1);
  1356. mdelay(5);
  1357. rtl9300_sds_field_w(sds_num, page, 0x15, 4, 4, 0x0);
  1358. }
  1359. /* Force PHY modes on 10GBit Serdes
  1360. */
  1361. void rtl9300_force_sds_mode(int sds, phy_interface_t phy_if)
  1362. {
  1363. int lc_value;
  1364. int sds_mode;
  1365. bool lc_on;
  1366. int lane_0 = (sds % 2) ? sds - 1 : sds;
  1367. u32 v;
  1368. pr_info("%s: SDS: %d, mode %d\n", __func__, sds, phy_if);
  1369. switch (phy_if) {
  1370. case PHY_INTERFACE_MODE_SGMII:
  1371. sds_mode = RTL930X_SDS_MODE_SGMII;
  1372. lc_on = false;
  1373. lc_value = 0x1;
  1374. break;
  1375. case PHY_INTERFACE_MODE_HSGMII:
  1376. sds_mode = RTL930X_SDS_MODE_HSGMII;
  1377. lc_value = 0x3;
  1378. /* Configure LC */
  1379. break;
  1380. case PHY_INTERFACE_MODE_1000BASEX:
  1381. sds_mode = RTL930X_SDS_MODE_1000BASEX;
  1382. lc_on = false;
  1383. break;
  1384. case PHY_INTERFACE_MODE_2500BASEX:
  1385. sds_mode = RTL930X_SDS_MODE_2500BASEX;
  1386. lc_value = 0x3;
  1387. /* Configure LC */
  1388. break;
  1389. case PHY_INTERFACE_MODE_10GBASER:
  1390. sds_mode = RTL930X_SDS_MODE_10GBASER;
  1391. lc_on = true;
  1392. lc_value = 0x5;
  1393. break;
  1394. case PHY_INTERFACE_MODE_NA:
  1395. /* This will disable SerDes */
  1396. sds_mode = RTL930X_SDS_OFF;
  1397. break;
  1398. default:
  1399. pr_err("%s: unknown serdes mode: %s\n",
  1400. __func__, phy_modes(phy_if));
  1401. return;
  1402. }
  1403. pr_info("%s --------------------- serdes %d forcing to %x ...\n", __func__, sds, sds_mode);
  1404. /* Power down SerDes */
  1405. rtl9300_sds_field_w(sds, 0x20, 0, 7, 6, 0x3);
  1406. if (sds == 5) pr_info("%s after %x\n", __func__, rtl930x_read_sds_phy(sds, 0x20, 0));
  1407. if (sds == 5) pr_info("%s a %x\n", __func__, rtl930x_read_sds_phy(sds, 0x1f, 9));
  1408. /* Force mode enable */
  1409. rtl9300_sds_field_w(sds, 0x1f, 9, 6, 6, 0x1);
  1410. if (sds == 5) pr_info("%s b %x\n", __func__, rtl930x_read_sds_phy(sds, 0x1f, 9));
  1411. /* SerDes off */
  1412. rtl9300_sds_field_w(sds, 0x1f, 9, 11, 7, RTL930X_SDS_OFF);
  1413. if (phy_if == PHY_INTERFACE_MODE_NA)
  1414. return;
  1415. if (sds == 5) pr_info("%s c %x\n", __func__, rtl930x_read_sds_phy(sds, 0x20, 18));
  1416. /* Enable LC and ring */
  1417. rtl9300_sds_field_w(lane_0, 0x20, 18, 3, 0, 0xf);
  1418. if (sds == lane_0)
  1419. rtl9300_sds_field_w(lane_0, 0x20, 18, 5, 4, 0x1);
  1420. else
  1421. rtl9300_sds_field_w(lane_0, 0x20, 18, 7, 6, 0x1);
  1422. rtl9300_sds_field_w(sds, 0x20, 0, 5, 4, 0x3);
  1423. if (lc_on)
  1424. rtl9300_sds_field_w(lane_0, 0x20, 18, 11, 8, lc_value);
  1425. else
  1426. rtl9300_sds_field_w(lane_0, 0x20, 18, 15, 12, lc_value);
  1427. /* Force analog LC & ring on */
  1428. rtl9300_sds_field_w(lane_0, 0x21, 11, 3, 0, 0xf);
  1429. v = lc_on ? 0x3 : 0x1;
  1430. if (sds == lane_0)
  1431. rtl9300_sds_field_w(lane_0, 0x20, 18, 5, 4, v);
  1432. else
  1433. rtl9300_sds_field_w(lane_0, 0x20, 18, 7, 6, v);
  1434. /* Force SerDes mode */
  1435. rtl9300_sds_field_w(sds, 0x1f, 9, 6, 6, 1);
  1436. rtl9300_sds_field_w(sds, 0x1f, 9, 11, 7, sds_mode);
  1437. /* Toggle LC or Ring */
  1438. for (int i = 0; i < 20; i++) {
  1439. u32 cr_0, cr_1, cr_2;
  1440. u32 m_bit, l_bit;
  1441. mdelay(200);
  1442. rtl930x_write_sds_phy(lane_0, 0x1f, 2, 53);
  1443. m_bit = (lane_0 == sds) ? (4) : (5);
  1444. l_bit = (lane_0 == sds) ? (4) : (5);
  1445. cr_0 = rtl9300_sds_field_r(lane_0, 0x1f, 20, m_bit, l_bit);
  1446. mdelay(10);
  1447. cr_1 = rtl9300_sds_field_r(lane_0, 0x1f, 20, m_bit, l_bit);
  1448. mdelay(10);
  1449. cr_2 = rtl9300_sds_field_r(lane_0, 0x1f, 20, m_bit, l_bit);
  1450. if (cr_0 && cr_1 && cr_2) {
  1451. u32 t;
  1452. if (phy_if != PHY_INTERFACE_MODE_10GBASER)
  1453. break;
  1454. t = rtl9300_sds_field_r(sds, 0x6, 0x1, 2, 2);
  1455. rtl9300_sds_field_w(sds, 0x6, 0x1, 2, 2, 0x1);
  1456. /* Reset FSM */
  1457. rtl9300_sds_field_w(sds, 0x6, 0x2, 12, 12, 0x1);
  1458. mdelay(10);
  1459. rtl9300_sds_field_w(sds, 0x6, 0x2, 12, 12, 0x0);
  1460. mdelay(10);
  1461. /* Need to read this twice */
  1462. v = rtl9300_sds_field_r(sds, 0x5, 0, 12, 12);
  1463. v = rtl9300_sds_field_r(sds, 0x5, 0, 12, 12);
  1464. rtl9300_sds_field_w(sds, 0x6, 0x1, 2, 2, t);
  1465. /* Reset FSM again */
  1466. rtl9300_sds_field_w(sds, 0x6, 0x2, 12, 12, 0x1);
  1467. mdelay(10);
  1468. rtl9300_sds_field_w(sds, 0x6, 0x2, 12, 12, 0x0);
  1469. mdelay(10);
  1470. if (v == 1)
  1471. break;
  1472. }
  1473. m_bit = (phy_if == PHY_INTERFACE_MODE_10GBASER) ? 3 : 1;
  1474. l_bit = (phy_if == PHY_INTERFACE_MODE_10GBASER) ? 2 : 0;
  1475. rtl9300_sds_field_w(lane_0, 0x21, 11, m_bit, l_bit, 0x2);
  1476. mdelay(10);
  1477. rtl9300_sds_field_w(lane_0, 0x21, 11, m_bit, l_bit, 0x3);
  1478. }
  1479. rtl930x_sds_rx_rst(sds, phy_if);
  1480. /* Re-enable power */
  1481. rtl9300_sds_field_w(sds, 0x20, 0, 7, 6, 0);
  1482. pr_info("%s --------------------- serdes %d forced to %x DONE\n", __func__, sds, sds_mode);
  1483. }
  1484. void rtl9300_sds_tx_config(int sds, phy_interface_t phy_if)
  1485. {
  1486. /* parameters: rtl9303_80G_txParam_s2 */
  1487. int impedance = 0x8;
  1488. int pre_amp = 0x2;
  1489. int main_amp = 0x9;
  1490. int post_amp = 0x2;
  1491. int pre_en = 0x1;
  1492. int post_en = 0x1;
  1493. int page;
  1494. switch(phy_if) {
  1495. case PHY_INTERFACE_MODE_1000BASEX:
  1496. pre_amp = 0x1;
  1497. main_amp = 0x9;
  1498. post_amp = 0x1;
  1499. page = 0x25;
  1500. break;
  1501. case PHY_INTERFACE_MODE_HSGMII:
  1502. case PHY_INTERFACE_MODE_2500BASEX:
  1503. pre_amp = 0;
  1504. post_amp = 0x8;
  1505. pre_en = 0;
  1506. page = 0x29;
  1507. break;
  1508. case PHY_INTERFACE_MODE_10GBASER:
  1509. case PHY_INTERFACE_MODE_USXGMII:
  1510. case PHY_INTERFACE_MODE_XGMII:
  1511. pre_en = 0;
  1512. pre_amp = 0;
  1513. main_amp = 0x10;
  1514. post_amp = 0;
  1515. post_en = 0;
  1516. page = 0x2f;
  1517. break;
  1518. default:
  1519. pr_err("%s: unsupported PHY mode\n", __func__);
  1520. return;
  1521. }
  1522. rtl9300_sds_field_w(sds, page, 0x01, 15, 11, pre_amp);
  1523. rtl9300_sds_field_w(sds, page, 0x06, 4, 0, post_amp);
  1524. rtl9300_sds_field_w(sds, page, 0x07, 0, 0, pre_en);
  1525. rtl9300_sds_field_w(sds, page, 0x07, 3, 3, post_en);
  1526. rtl9300_sds_field_w(sds, page, 0x07, 8, 4, main_amp);
  1527. rtl9300_sds_field_w(sds, page, 0x18, 15, 12, impedance);
  1528. }
  1529. /* Wait for clock ready, this assumes the SerDes is in XGMII mode
  1530. * timeout is in ms
  1531. */
  1532. int rtl9300_sds_clock_wait(int timeout)
  1533. {
  1534. u32 v;
  1535. unsigned long start = jiffies;
  1536. do {
  1537. rtl9300_sds_field_w(2, 0x1f, 0x2, 15, 0, 53);
  1538. v = rtl9300_sds_field_r(2, 0x1f, 20, 5, 4);
  1539. if (v == 3)
  1540. return 0;
  1541. } while (jiffies < start + (HZ / 1000) * timeout);
  1542. return 1;
  1543. }
  1544. void rtl9300_serdes_mac_link_config(int sds, bool tx_normal, bool rx_normal)
  1545. {
  1546. u32 v10, v1;
  1547. v10 = rtl930x_read_sds_phy(sds, 6, 2); /* 10GBit, page 6, reg 2 */
  1548. v1 = rtl930x_read_sds_phy(sds, 0, 0); /* 1GBit, page 0, reg 0 */
  1549. pr_info("%s: registers before %08x %08x\n", __func__, v10, v1);
  1550. v10 &= ~(BIT(13) | BIT(14));
  1551. v1 &= ~(BIT(8) | BIT(9));
  1552. v10 |= rx_normal ? 0 : BIT(13);
  1553. v1 |= rx_normal ? 0 : BIT(9);
  1554. v10 |= tx_normal ? 0 : BIT(14);
  1555. v1 |= tx_normal ? 0 : BIT(8);
  1556. rtl930x_write_sds_phy(sds, 6, 2, v10);
  1557. rtl930x_write_sds_phy(sds, 0, 0, v1);
  1558. v10 = rtl930x_read_sds_phy(sds, 6, 2);
  1559. v1 = rtl930x_read_sds_phy(sds, 0, 0);
  1560. pr_info("%s: registers after %08x %08x\n", __func__, v10, v1);
  1561. }
  1562. void rtl9300_sds_rxcal_dcvs_manual(u32 sds_num, u32 dcvs_id, bool manual, u32 dvcs_list[])
  1563. {
  1564. if (manual) {
  1565. switch(dcvs_id) {
  1566. case 0:
  1567. rtl9300_sds_field_w(sds_num, 0x2e, 0x1e, 14, 14, 0x1);
  1568. rtl9300_sds_field_w(sds_num, 0x2f, 0x03, 5, 5, dvcs_list[0]);
  1569. rtl9300_sds_field_w(sds_num, 0x2f, 0x03, 4, 0, dvcs_list[1]);
  1570. break;
  1571. case 1:
  1572. rtl9300_sds_field_w(sds_num, 0x2e, 0x1e, 13, 13, 0x1);
  1573. rtl9300_sds_field_w(sds_num, 0x2e, 0x1d, 15, 15, dvcs_list[0]);
  1574. rtl9300_sds_field_w(sds_num, 0x2e, 0x1d, 14, 11, dvcs_list[1]);
  1575. break;
  1576. case 2:
  1577. rtl9300_sds_field_w(sds_num, 0x2e, 0x1e, 12, 12, 0x1);
  1578. rtl9300_sds_field_w(sds_num, 0x2e, 0x1d, 10, 10, dvcs_list[0]);
  1579. rtl9300_sds_field_w(sds_num, 0x2e, 0x1d, 9, 6, dvcs_list[1]);
  1580. break;
  1581. case 3:
  1582. rtl9300_sds_field_w(sds_num, 0x2e, 0x1e, 11, 11, 0x1);
  1583. rtl9300_sds_field_w(sds_num, 0x2e, 0x1d, 5, 5, dvcs_list[0]);
  1584. rtl9300_sds_field_w(sds_num, 0x2e, 0x1d, 4, 1, dvcs_list[1]);
  1585. break;
  1586. case 4:
  1587. rtl9300_sds_field_w(sds_num, 0x2e, 0x01, 15, 15, 0x1);
  1588. rtl9300_sds_field_w(sds_num, 0x2e, 0x11, 10, 10, dvcs_list[0]);
  1589. rtl9300_sds_field_w(sds_num, 0x2e, 0x11, 9, 6, dvcs_list[1]);
  1590. break;
  1591. case 5:
  1592. rtl9300_sds_field_w(sds_num, 0x2e, 0x02, 11, 11, 0x1);
  1593. rtl9300_sds_field_w(sds_num, 0x2e, 0x11, 4, 4, dvcs_list[0]);
  1594. rtl9300_sds_field_w(sds_num, 0x2e, 0x11, 3, 0, dvcs_list[1]);
  1595. break;
  1596. default:
  1597. break;
  1598. }
  1599. } else {
  1600. switch(dcvs_id) {
  1601. case 0:
  1602. rtl9300_sds_field_w(sds_num, 0x2e, 0x1e, 14, 14, 0x0);
  1603. break;
  1604. case 1:
  1605. rtl9300_sds_field_w(sds_num, 0x2e, 0x1e, 13, 13, 0x0);
  1606. break;
  1607. case 2:
  1608. rtl9300_sds_field_w(sds_num, 0x2e, 0x1e, 12, 12, 0x0);
  1609. break;
  1610. case 3:
  1611. rtl9300_sds_field_w(sds_num, 0x2e, 0x1e, 11, 11, 0x0);
  1612. break;
  1613. case 4:
  1614. rtl9300_sds_field_w(sds_num, 0x2e, 0x01, 15, 15, 0x0);
  1615. break;
  1616. case 5:
  1617. rtl9300_sds_field_w(sds_num, 0x2e, 0x02, 11, 11, 0x0);
  1618. break;
  1619. default:
  1620. break;
  1621. }
  1622. mdelay(1);
  1623. }
  1624. }
  1625. void rtl9300_sds_rxcal_dcvs_get(u32 sds_num, u32 dcvs_id, u32 dcvs_list[])
  1626. {
  1627. u32 dcvs_sign_out = 0, dcvs_coef_bin = 0;
  1628. bool dcvs_manual;
  1629. if (!(sds_num % 2))
  1630. rtl930x_write_sds_phy(sds_num, 0x1f, 0x2, 0x2f);
  1631. else
  1632. rtl930x_write_sds_phy(sds_num - 1, 0x1f, 0x2, 0x31);
  1633. /* ##Page0x2E, Reg0x15[9], REG0_RX_EN_TEST=[1] */
  1634. rtl9300_sds_field_w(sds_num, 0x2e, 0x15, 9, 9, 0x1);
  1635. /* ##Page0x21, Reg0x06[11 6], REG0_RX_DEBUG_SEL=[1 0 x x x x] */
  1636. rtl9300_sds_field_w(sds_num, 0x21, 0x06, 11, 6, 0x20);
  1637. switch(dcvs_id) {
  1638. case 0:
  1639. rtl9300_sds_field_w(sds_num, 0x2f, 0x0c, 5, 0, 0x22);
  1640. mdelay(1);
  1641. /* ##DCVS0 Read Out */
  1642. dcvs_sign_out = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 4, 4);
  1643. dcvs_coef_bin = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 3, 0);
  1644. dcvs_manual = !!rtl9300_sds_field_r(sds_num, 0x2e, 0x1e, 14, 14);
  1645. break;
  1646. case 1:
  1647. rtl9300_sds_field_w(sds_num, 0x2f, 0x0c, 5, 0, 0x23);
  1648. mdelay(1);
  1649. /* ##DCVS0 Read Out */
  1650. dcvs_coef_bin = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 4, 4);
  1651. dcvs_coef_bin = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 3, 0);
  1652. dcvs_manual = !!rtl9300_sds_field_r(sds_num, 0x2e, 0x1e, 13, 13);
  1653. break;
  1654. case 2:
  1655. rtl9300_sds_field_w(sds_num, 0x2f, 0x0c, 5, 0, 0x24);
  1656. mdelay(1);
  1657. /* ##DCVS0 Read Out */
  1658. dcvs_sign_out = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 4, 4);
  1659. dcvs_coef_bin = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 3, 0);
  1660. dcvs_manual = !!rtl9300_sds_field_r(sds_num, 0x2e, 0x1e, 12, 12);
  1661. break;
  1662. case 3:
  1663. rtl9300_sds_field_w(sds_num, 0x2f, 0x0c, 5, 0, 0x25);
  1664. mdelay(1);
  1665. /* ##DCVS0 Read Out */
  1666. dcvs_sign_out = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 4, 4);
  1667. dcvs_coef_bin = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 3, 0);
  1668. dcvs_manual = rtl9300_sds_field_r(sds_num, 0x2e, 0x1e, 11, 11);
  1669. break;
  1670. case 4:
  1671. rtl9300_sds_field_w(sds_num, 0x2f, 0x0c, 5, 0, 0x2c);
  1672. mdelay(1);
  1673. /* ##DCVS0 Read Out */
  1674. dcvs_sign_out = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 4, 4);
  1675. dcvs_coef_bin = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 3, 0);
  1676. dcvs_manual = !!rtl9300_sds_field_r(sds_num, 0x2e, 0x01, 15, 15);
  1677. break;
  1678. case 5:
  1679. rtl9300_sds_field_w(sds_num, 0x2f, 0x0c, 5, 0, 0x2d);
  1680. mdelay(1);
  1681. /* ##DCVS0 Read Out */
  1682. dcvs_sign_out = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 4, 4);
  1683. dcvs_coef_bin = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 3, 0);
  1684. dcvs_manual = rtl9300_sds_field_r(sds_num, 0x2e, 0x02, 11, 11);
  1685. break;
  1686. default:
  1687. break;
  1688. }
  1689. if (dcvs_sign_out)
  1690. pr_info("%s DCVS %u Sign: -", __func__, dcvs_id);
  1691. else
  1692. pr_info("%s DCVS %u Sign: +", __func__, dcvs_id);
  1693. pr_info("DCVS %u even coefficient = %u", dcvs_id, dcvs_coef_bin);
  1694. pr_info("DCVS %u manual = %u", dcvs_id, dcvs_manual);
  1695. dcvs_list[0] = dcvs_sign_out;
  1696. dcvs_list[1] = dcvs_coef_bin;
  1697. }
  1698. void rtl9300_sds_rxcal_leq_manual(u32 sds_num, bool manual, u32 leq_gray)
  1699. {
  1700. if (manual) {
  1701. rtl9300_sds_field_w(sds_num, 0x2e, 0x18, 15, 15, 0x1);
  1702. rtl9300_sds_field_w(sds_num, 0x2e, 0x16, 14, 10, leq_gray);
  1703. } else {
  1704. rtl9300_sds_field_w(sds_num, 0x2e, 0x18, 15, 15, 0x0);
  1705. mdelay(100);
  1706. }
  1707. }
  1708. void rtl9300_sds_rxcal_leq_offset_manual(u32 sds_num, bool manual, u32 offset)
  1709. {
  1710. if (manual) {
  1711. rtl9300_sds_field_w(sds_num, 0x2e, 0x17, 6, 2, offset);
  1712. } else {
  1713. rtl9300_sds_field_w(sds_num, 0x2e, 0x17, 6, 2, offset);
  1714. mdelay(1);
  1715. }
  1716. }
  1717. #define GRAY_BITS 5
  1718. u32 rtl9300_sds_rxcal_gray_to_binary(u32 gray_code)
  1719. {
  1720. int i, j, m;
  1721. u32 g[GRAY_BITS];
  1722. u32 c[GRAY_BITS];
  1723. u32 leq_binary = 0;
  1724. for(i = 0; i < GRAY_BITS; i++)
  1725. g[i] = (gray_code & BIT(i)) >> i;
  1726. m = GRAY_BITS - 1;
  1727. c[m] = g[m];
  1728. for(i = 0; i < m; i++) {
  1729. c[i] = g[i];
  1730. for(j = i + 1; j < GRAY_BITS; j++)
  1731. c[i] = c[i] ^ g[j];
  1732. }
  1733. for(i = 0; i < GRAY_BITS; i++)
  1734. leq_binary += c[i] << i;
  1735. return leq_binary;
  1736. }
  1737. u32 rtl9300_sds_rxcal_leq_read(int sds_num)
  1738. {
  1739. u32 leq_gray, leq_bin;
  1740. bool leq_manual;
  1741. if (!(sds_num % 2))
  1742. rtl930x_write_sds_phy(sds_num, 0x1f, 0x2, 0x2f);
  1743. else
  1744. rtl930x_write_sds_phy(sds_num - 1, 0x1f, 0x2, 0x31);
  1745. /* ##Page0x2E, Reg0x15[9], REG0_RX_EN_TEST=[1] */
  1746. rtl9300_sds_field_w(sds_num, 0x2e, 0x15, 9, 9, 0x1);
  1747. /* ##Page0x21, Reg0x06[11 6], REG0_RX_DEBUG_SEL=[0 1 x x x x] */
  1748. rtl9300_sds_field_w(sds_num, 0x21, 0x06, 11, 6, 0x10);
  1749. mdelay(1);
  1750. /* ##LEQ Read Out */
  1751. leq_gray = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 7, 3);
  1752. leq_manual = !!rtl9300_sds_field_r(sds_num, 0x2e, 0x18, 15, 15);
  1753. leq_bin = rtl9300_sds_rxcal_gray_to_binary(leq_gray);
  1754. pr_info("LEQ_gray: %u, LEQ_bin: %u", leq_gray, leq_bin);
  1755. pr_info("LEQ manual: %u", leq_manual);
  1756. return leq_bin;
  1757. }
  1758. void rtl9300_sds_rxcal_vth_manual(u32 sds_num, bool manual, u32 vth_list[])
  1759. {
  1760. if (manual) {
  1761. rtl9300_sds_field_w(sds_num, 0x2e, 0x0f, 13, 13, 0x1);
  1762. rtl9300_sds_field_w(sds_num, 0x2e, 0x13, 5, 3, vth_list[0]);
  1763. rtl9300_sds_field_w(sds_num, 0x2e, 0x13, 2, 0, vth_list[1]);
  1764. } else {
  1765. rtl9300_sds_field_w(sds_num, 0x2e, 0x0f, 13, 13, 0x0);
  1766. mdelay(10);
  1767. }
  1768. }
  1769. void rtl9300_sds_rxcal_vth_get(u32 sds_num, u32 vth_list[])
  1770. {
  1771. u32 vth_manual;
  1772. /* ##Page0x1F, Reg0x02[15 0], REG_DBGO_SEL=[0x002F]; */ /* Lane0 */
  1773. /* ##Page0x1F, Reg0x02[15 0], REG_DBGO_SEL=[0x0031]; */ /* Lane1 */
  1774. if (!(sds_num % 2))
  1775. rtl930x_write_sds_phy(sds_num, 0x1f, 0x2, 0x2f);
  1776. else
  1777. rtl930x_write_sds_phy(sds_num - 1, 0x1f, 0x2, 0x31);
  1778. /* ##Page0x2E, Reg0x15[9], REG0_RX_EN_TEST=[1] */
  1779. rtl9300_sds_field_w(sds_num, 0x2e, 0x15, 9, 9, 0x1);
  1780. /* ##Page0x21, Reg0x06[11 6], REG0_RX_DEBUG_SEL=[1 0 x x x x] */
  1781. rtl9300_sds_field_w(sds_num, 0x21, 0x06, 11, 6, 0x20);
  1782. /* ##Page0x2F, Reg0x0C[5 0], REG0_COEF_SEL=[0 0 1 1 0 0] */
  1783. rtl9300_sds_field_w(sds_num, 0x2f, 0x0c, 5, 0, 0xc);
  1784. mdelay(1);
  1785. /* ##VthP & VthN Read Out */
  1786. vth_list[0] = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 2, 0); /* v_thp set bin */
  1787. vth_list[1] = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 5, 3); /* v_thn set bin */
  1788. pr_info("vth_set_bin = %d", vth_list[0]);
  1789. pr_info("vth_set_bin = %d", vth_list[1]);
  1790. vth_manual = !!rtl9300_sds_field_r(sds_num, 0x2e, 0x0f, 13, 13);
  1791. pr_info("Vth Maunal = %d", vth_manual);
  1792. }
  1793. void rtl9300_sds_rxcal_tap_manual(u32 sds_num, int tap_id, bool manual, u32 tap_list[])
  1794. {
  1795. if (manual) {
  1796. switch(tap_id) {
  1797. case 0:
  1798. /* ##REG0_LOAD_IN_INIT[0]=1; REG0_TAP0_INIT[5:0]=Tap0_Value */
  1799. rtl9300_sds_field_w(sds_num, 0x2e, 0x0f, tap_id + 7, tap_id + 7, 0x1);
  1800. rtl9300_sds_field_w(sds_num, 0x2f, 0x03, 5, 5, tap_list[0]);
  1801. rtl9300_sds_field_w(sds_num, 0x2f, 0x03, 4, 0, tap_list[1]);
  1802. break;
  1803. case 1:
  1804. rtl9300_sds_field_w(sds_num, 0x2e, 0x0f, tap_id + 7, tap_id + 7, 0x1);
  1805. rtl9300_sds_field_w(sds_num, 0x21, 0x07, 6, 6, tap_list[0]);
  1806. rtl9300_sds_field_w(sds_num, 0x2e, 0x09, 11, 6, tap_list[1]);
  1807. rtl9300_sds_field_w(sds_num, 0x21, 0x07, 5, 5, tap_list[2]);
  1808. rtl9300_sds_field_w(sds_num, 0x2f, 0x12, 5, 0, tap_list[3]);
  1809. break;
  1810. case 2:
  1811. rtl9300_sds_field_w(sds_num, 0x2e, 0x0f, tap_id + 7, tap_id + 7, 0x1);
  1812. rtl9300_sds_field_w(sds_num, 0x2e, 0x09, 5, 5, tap_list[0]);
  1813. rtl9300_sds_field_w(sds_num, 0x2e, 0x09, 4, 0, tap_list[1]);
  1814. rtl9300_sds_field_w(sds_num, 0x2e, 0x0a, 11, 11, tap_list[2]);
  1815. rtl9300_sds_field_w(sds_num, 0x2e, 0x0a, 10, 6, tap_list[3]);
  1816. break;
  1817. case 3:
  1818. rtl9300_sds_field_w(sds_num, 0x2e, 0x0f, tap_id + 7, tap_id + 7, 0x1);
  1819. rtl9300_sds_field_w(sds_num, 0x2e, 0x0a, 5, 5, tap_list[0]);
  1820. rtl9300_sds_field_w(sds_num, 0x2e, 0x0a, 4, 0, tap_list[1]);
  1821. rtl9300_sds_field_w(sds_num, 0x2e, 0x06, 5, 5, tap_list[2]);
  1822. rtl9300_sds_field_w(sds_num, 0x2e, 0x06, 4, 0, tap_list[3]);
  1823. break;
  1824. case 4:
  1825. rtl9300_sds_field_w(sds_num, 0x2e, 0x0f, tap_id + 7, tap_id + 7, 0x1);
  1826. rtl9300_sds_field_w(sds_num, 0x2f, 0x01, 5, 5, tap_list[0]);
  1827. rtl9300_sds_field_w(sds_num, 0x2f, 0x01, 4, 0, tap_list[1]);
  1828. rtl9300_sds_field_w(sds_num, 0x2e, 0x06, 11, 11, tap_list[2]);
  1829. rtl9300_sds_field_w(sds_num, 0x2e, 0x06, 10, 6, tap_list[3]);
  1830. break;
  1831. default:
  1832. break;
  1833. }
  1834. } else {
  1835. rtl9300_sds_field_w(sds_num, 0x2e, 0x0f, tap_id + 7, tap_id + 7, 0x0);
  1836. mdelay(10);
  1837. }
  1838. }
  1839. void rtl9300_sds_rxcal_tap_get(u32 sds_num, u32 tap_id, u32 tap_list[])
  1840. {
  1841. u32 tap0_sign_out;
  1842. u32 tap0_coef_bin;
  1843. u32 tap_sign_out_even;
  1844. u32 tap_coef_bin_even;
  1845. u32 tap_sign_out_odd;
  1846. u32 tap_coef_bin_odd;
  1847. bool tap_manual;
  1848. if (!(sds_num % 2))
  1849. rtl930x_write_sds_phy(sds_num, 0x1f, 0x2, 0x2f);
  1850. else
  1851. rtl930x_write_sds_phy(sds_num - 1, 0x1f, 0x2, 0x31);
  1852. /* ##Page0x2E, Reg0x15[9], REG0_RX_EN_TEST=[1] */
  1853. rtl9300_sds_field_w(sds_num, 0x2e, 0x15, 9, 9, 0x1);
  1854. /* ##Page0x21, Reg0x06[11 6], REG0_RX_DEBUG_SEL=[1 0 x x x x] */
  1855. rtl9300_sds_field_w(sds_num, 0x21, 0x06, 11, 6, 0x20);
  1856. if (!tap_id) {
  1857. /* ##Page0x2F, Reg0x0C[5 0], REG0_COEF_SEL=[0 0 0 0 0 1] */
  1858. rtl9300_sds_field_w(sds_num, 0x2f, 0x0c, 5, 0, 0);
  1859. /* ##Tap1 Even Read Out */
  1860. mdelay(1);
  1861. tap0_sign_out = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 5, 5);
  1862. tap0_coef_bin = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 4, 0);
  1863. if (tap0_sign_out == 1)
  1864. pr_info("Tap0 Sign : -");
  1865. else
  1866. pr_info("Tap0 Sign : +");
  1867. pr_info("tap0_coef_bin = %d", tap0_coef_bin);
  1868. tap_list[0] = tap0_sign_out;
  1869. tap_list[1] = tap0_coef_bin;
  1870. tap_manual = !!rtl9300_sds_field_r(sds_num, 0x2e, 0x0f, 7, 7);
  1871. pr_info("tap0 manual = %u",tap_manual);
  1872. } else {
  1873. /* ##Page0x2F, Reg0x0C[5 0], REG0_COEF_SEL=[0 0 0 0 0 1] */
  1874. rtl9300_sds_field_w(sds_num, 0x2f, 0x0c, 5, 0, tap_id);
  1875. mdelay(1);
  1876. /* ##Tap1 Even Read Out */
  1877. tap_sign_out_even = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 5, 5);
  1878. tap_coef_bin_even = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 4, 0);
  1879. /* ##Page0x2F, Reg0x0C[5 0], REG0_COEF_SEL=[0 0 0 1 1 0] */
  1880. rtl9300_sds_field_w(sds_num, 0x2f, 0x0c, 5, 0, (tap_id + 5));
  1881. /* ##Tap1 Odd Read Out */
  1882. tap_sign_out_odd = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 5, 5);
  1883. tap_coef_bin_odd = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 4, 0);
  1884. if (tap_sign_out_even == 1)
  1885. pr_info("Tap %u even sign: -", tap_id);
  1886. else
  1887. pr_info("Tap %u even sign: +", tap_id);
  1888. pr_info("Tap %u even coefficient = %u", tap_id, tap_coef_bin_even);
  1889. if (tap_sign_out_odd == 1)
  1890. pr_info("Tap %u odd sign: -", tap_id);
  1891. else
  1892. pr_info("Tap %u odd sign: +", tap_id);
  1893. pr_info("Tap %u odd coefficient = %u", tap_id,tap_coef_bin_odd);
  1894. tap_list[0] = tap_sign_out_even;
  1895. tap_list[1] = tap_coef_bin_even;
  1896. tap_list[2] = tap_sign_out_odd;
  1897. tap_list[3] = tap_coef_bin_odd;
  1898. tap_manual = rtl9300_sds_field_r(sds_num, 0x2e, 0x0f, tap_id + 7, tap_id + 7);
  1899. pr_info("tap %u manual = %d",tap_id, tap_manual);
  1900. }
  1901. }
  1902. void rtl9300_do_rx_calibration_1(int sds, phy_interface_t phy_mode)
  1903. {
  1904. /* From both rtl9300_rxCaliConf_serdes_myParam and rtl9300_rxCaliConf_phy_myParam */
  1905. int tap0_init_val = 0x1f; /* Initial Decision Fed Equalizer 0 tap */
  1906. int vth_min = 0x0;
  1907. pr_info("start_1.1.1 initial value for sds %d\n", sds);
  1908. rtl930x_write_sds_phy(sds, 6, 0, 0);
  1909. /* FGCAL */
  1910. rtl9300_sds_field_w(sds, 0x2e, 0x01, 14, 14, 0x00);
  1911. rtl9300_sds_field_w(sds, 0x2e, 0x1c, 10, 5, 0x20);
  1912. rtl9300_sds_field_w(sds, 0x2f, 0x02, 0, 0, 0x01);
  1913. /* DCVS */
  1914. rtl9300_sds_field_w(sds, 0x2e, 0x1e, 14, 11, 0x00);
  1915. rtl9300_sds_field_w(sds, 0x2e, 0x01, 15, 15, 0x00);
  1916. rtl9300_sds_field_w(sds, 0x2e, 0x02, 11, 11, 0x00);
  1917. rtl9300_sds_field_w(sds, 0x2e, 0x1c, 4, 0, 0x00);
  1918. rtl9300_sds_field_w(sds, 0x2e, 0x1d, 15, 11, 0x00);
  1919. rtl9300_sds_field_w(sds, 0x2e, 0x1d, 10, 6, 0x00);
  1920. rtl9300_sds_field_w(sds, 0x2e, 0x1d, 5, 1, 0x00);
  1921. rtl9300_sds_field_w(sds, 0x2e, 0x02, 10, 6, 0x00);
  1922. rtl9300_sds_field_w(sds, 0x2e, 0x11, 4, 0, 0x00);
  1923. rtl9300_sds_field_w(sds, 0x2f, 0x00, 3, 0, 0x0f);
  1924. rtl9300_sds_field_w(sds, 0x2e, 0x04, 6, 6, 0x01);
  1925. rtl9300_sds_field_w(sds, 0x2e, 0x04, 7, 7, 0x01);
  1926. /* LEQ (Long Term Equivalent signal level) */
  1927. rtl9300_sds_field_w(sds, 0x2e, 0x16, 14, 8, 0x00);
  1928. /* DFE (Decision Fed Equalizer) */
  1929. rtl9300_sds_field_w(sds, 0x2f, 0x03, 5, 0, tap0_init_val);
  1930. rtl9300_sds_field_w(sds, 0x2e, 0x09, 11, 6, 0x00);
  1931. rtl9300_sds_field_w(sds, 0x2e, 0x09, 5, 0, 0x00);
  1932. rtl9300_sds_field_w(sds, 0x2e, 0x0a, 5, 0, 0x00);
  1933. rtl9300_sds_field_w(sds, 0x2f, 0x01, 5, 0, 0x00);
  1934. rtl9300_sds_field_w(sds, 0x2f, 0x12, 5, 0, 0x00);
  1935. rtl9300_sds_field_w(sds, 0x2e, 0x0a, 11, 6, 0x00);
  1936. rtl9300_sds_field_w(sds, 0x2e, 0x06, 5, 0, 0x00);
  1937. rtl9300_sds_field_w(sds, 0x2f, 0x01, 5, 0, 0x00);
  1938. /* Vth */
  1939. rtl9300_sds_field_w(sds, 0x2e, 0x13, 5, 3, 0x07);
  1940. rtl9300_sds_field_w(sds, 0x2e, 0x13, 2, 0, 0x07);
  1941. rtl9300_sds_field_w(sds, 0x2f, 0x0b, 5, 3, vth_min);
  1942. pr_info("end_1.1.1 --\n");
  1943. pr_info("start_1.1.2 Load DFE init. value\n");
  1944. rtl9300_sds_field_w(sds, 0x2e, 0x0f, 13, 7, 0x7f);
  1945. pr_info("end_1.1.2\n");
  1946. pr_info("start_1.1.3 disable LEQ training,enable DFE clock\n");
  1947. rtl9300_sds_field_w(sds, 0x2e, 0x17, 7, 7, 0x00);
  1948. rtl9300_sds_field_w(sds, 0x2e, 0x17, 6, 2, 0x00);
  1949. rtl9300_sds_field_w(sds, 0x2e, 0x0c, 8, 8, 0x00);
  1950. rtl9300_sds_field_w(sds, 0x2e, 0x0b, 4, 4, 0x01);
  1951. rtl9300_sds_field_w(sds, 0x2e, 0x12, 14, 14, 0x00);
  1952. rtl9300_sds_field_w(sds, 0x2f, 0x02, 15, 15, 0x00);
  1953. pr_info("end_1.1.3 --\n");
  1954. pr_info("start_1.1.4 offset cali setting\n");
  1955. rtl9300_sds_field_w(sds, 0x2e, 0x0f, 15, 14, 0x03);
  1956. pr_info("end_1.1.4\n");
  1957. pr_info("start_1.1.5 LEQ and DFE setting\n");
  1958. /* TODO: make this work for DAC cables of different lengths */
  1959. /* For a 10GBit serdes wit Fibre, SDS 8 or 9 */
  1960. if (phy_mode == PHY_INTERFACE_MODE_10GBASER || PHY_INTERFACE_MODE_1000BASEX)
  1961. rtl9300_sds_field_w(sds, 0x2e, 0x16, 3, 2, 0x02);
  1962. else
  1963. pr_err("%s not PHY-based or SerDes, implement DAC!\n", __func__);
  1964. /* No serdes, check for Aquantia PHYs */
  1965. rtl9300_sds_field_w(sds, 0x2e, 0x16, 3, 2, 0x02);
  1966. rtl9300_sds_field_w(sds, 0x2e, 0x0f, 6, 0, 0x5f);
  1967. rtl9300_sds_field_w(sds, 0x2f, 0x05, 7, 2, 0x1f);
  1968. rtl9300_sds_field_w(sds, 0x2e, 0x19, 9, 5, 0x1f);
  1969. rtl9300_sds_field_w(sds, 0x2f, 0x0b, 15, 9, 0x3c);
  1970. rtl9300_sds_field_w(sds, 0x2e, 0x0b, 1, 0, 0x03);
  1971. pr_info("end_1.1.5\n");
  1972. }
  1973. void rtl9300_do_rx_calibration_2_1(u32 sds_num)
  1974. {
  1975. pr_info("start_1.2.1 ForegroundOffsetCal_Manual\n");
  1976. /* Gray config endis to 1 */
  1977. rtl9300_sds_field_w(sds_num, 0x2f, 0x02, 2, 2, 0x01);
  1978. /* ForegroundOffsetCal_Manual(auto mode) */
  1979. rtl9300_sds_field_w(sds_num, 0x2e, 0x01, 14, 14, 0x00);
  1980. pr_info("end_1.2.1");
  1981. }
  1982. void rtl9300_do_rx_calibration_2_2(int sds_num)
  1983. {
  1984. /* Force Rx-Run = 0 */
  1985. rtl9300_sds_field_w(sds_num, 0x2e, 0x15, 8, 8, 0x0);
  1986. rtl930x_sds_rx_rst(sds_num, PHY_INTERFACE_MODE_10GBASER);
  1987. }
  1988. void rtl9300_do_rx_calibration_2_3(int sds_num)
  1989. {
  1990. u32 fgcal_binary, fgcal_gray;
  1991. u32 offset_range;
  1992. pr_info("start_1.2.3 Foreground Calibration\n");
  1993. while(1) {
  1994. if (!(sds_num % 2))
  1995. rtl930x_write_sds_phy(sds_num, 0x1f, 0x2, 0x2f);
  1996. else
  1997. rtl930x_write_sds_phy(sds_num -1 , 0x1f, 0x2, 0x31);
  1998. /* ##Page0x2E, Reg0x15[9], REG0_RX_EN_TEST=[1] */
  1999. rtl9300_sds_field_w(sds_num, 0x2e, 0x15, 9, 9, 0x1);
  2000. /* ##Page0x21, Reg0x06[11 6], REG0_RX_DEBUG_SEL=[1 0 x x x x] */
  2001. rtl9300_sds_field_w(sds_num, 0x21, 0x06, 11, 6, 0x20);
  2002. /* ##Page0x2F, Reg0x0C[5 0], REG0_COEF_SEL=[0 0 1 1 1 1] */
  2003. rtl9300_sds_field_w(sds_num, 0x2f, 0x0c, 5, 0, 0xf);
  2004. /* ##FGCAL read gray */
  2005. fgcal_gray = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 5, 0);
  2006. /* ##Page0x2F, Reg0x0C[5 0], REG0_COEF_SEL=[0 0 1 1 1 0] */
  2007. rtl9300_sds_field_w(sds_num, 0x2f, 0x0c, 5, 0, 0xe);
  2008. /* ##FGCAL read binary */
  2009. fgcal_binary = rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 5, 0);
  2010. pr_info("%s: fgcal_gray: %d, fgcal_binary %d\n",
  2011. __func__, fgcal_gray, fgcal_binary);
  2012. offset_range = rtl9300_sds_field_r(sds_num, 0x2e, 0x15, 15, 14);
  2013. if (fgcal_binary > 60 || fgcal_binary < 3) {
  2014. if (offset_range == 3) {
  2015. pr_info("%s: Foreground Calibration result marginal!", __func__);
  2016. break;
  2017. } else {
  2018. offset_range++;
  2019. rtl9300_sds_field_w(sds_num, 0x2e, 0x15, 15, 14, offset_range);
  2020. rtl9300_do_rx_calibration_2_2(sds_num);
  2021. }
  2022. } else {
  2023. break;
  2024. }
  2025. }
  2026. pr_info("%s: end_1.2.3\n", __func__);
  2027. }
  2028. void rtl9300_do_rx_calibration_2(int sds)
  2029. {
  2030. rtl930x_sds_rx_rst(sds, PHY_INTERFACE_MODE_10GBASER);
  2031. rtl9300_do_rx_calibration_2_1(sds);
  2032. rtl9300_do_rx_calibration_2_2(sds);
  2033. rtl9300_do_rx_calibration_2_3(sds);
  2034. }
  2035. void rtl9300_sds_rxcal_3_1(int sds_num, phy_interface_t phy_mode)
  2036. {
  2037. pr_info("start_1.3.1");
  2038. /* ##1.3.1 */
  2039. if (phy_mode != PHY_INTERFACE_MODE_10GBASER && phy_mode != PHY_INTERFACE_MODE_1000BASEX)
  2040. rtl9300_sds_field_w(sds_num, 0x2e, 0xc, 8, 8, 0);
  2041. rtl9300_sds_field_w(sds_num, 0x2e, 0x17, 7, 7, 0x0);
  2042. rtl9300_sds_rxcal_leq_manual(sds_num, false, 0);
  2043. pr_info("end_1.3.1");
  2044. }
  2045. void rtl9300_sds_rxcal_3_2(int sds_num, phy_interface_t phy_mode)
  2046. {
  2047. u32 sum10 = 0, avg10, int10;
  2048. int dac_long_cable_offset;
  2049. bool eq_hold_enabled;
  2050. int i;
  2051. if (phy_mode == PHY_INTERFACE_MODE_10GBASER || phy_mode == PHY_INTERFACE_MODE_1000BASEX) {
  2052. /* rtl9300_rxCaliConf_serdes_myParam */
  2053. dac_long_cable_offset = 3;
  2054. eq_hold_enabled = true;
  2055. } else {
  2056. /* rtl9300_rxCaliConf_phy_myParam */
  2057. dac_long_cable_offset = 0;
  2058. eq_hold_enabled = false;
  2059. }
  2060. if (phy_mode == PHY_INTERFACE_MODE_1000BASEX)
  2061. pr_warn("%s: LEQ only valid for 10GR!\n", __func__);
  2062. pr_info("start_1.3.2");
  2063. for(i = 0; i < 10; i++) {
  2064. sum10 += rtl9300_sds_rxcal_leq_read(sds_num);
  2065. mdelay(10);
  2066. }
  2067. avg10 = (sum10 / 10) + (((sum10 % 10) >= 5) ? 1 : 0);
  2068. int10 = sum10 / 10;
  2069. pr_info("sum10:%u, avg10:%u, int10:%u", sum10, avg10, int10);
  2070. if (phy_mode == PHY_INTERFACE_MODE_10GBASER || phy_mode == PHY_INTERFACE_MODE_1000BASEX) {
  2071. if (dac_long_cable_offset) {
  2072. rtl9300_sds_rxcal_leq_offset_manual(sds_num, 1, dac_long_cable_offset);
  2073. rtl9300_sds_field_w(sds_num, 0x2e, 0x17, 7, 7, eq_hold_enabled);
  2074. if (phy_mode == PHY_INTERFACE_MODE_10GBASER)
  2075. rtl9300_sds_rxcal_leq_manual(sds_num, true, avg10);
  2076. } else {
  2077. if (sum10 >= 5) {
  2078. rtl9300_sds_rxcal_leq_offset_manual(sds_num, 1, 3);
  2079. rtl9300_sds_field_w(sds_num, 0x2e, 0x17, 7, 7, 0x1);
  2080. if (phy_mode == PHY_INTERFACE_MODE_10GBASER)
  2081. rtl9300_sds_rxcal_leq_manual(sds_num, true, avg10);
  2082. } else {
  2083. rtl9300_sds_rxcal_leq_offset_manual(sds_num, 1, 0);
  2084. rtl9300_sds_field_w(sds_num, 0x2e, 0x17, 7, 7, 0x1);
  2085. if (phy_mode == PHY_INTERFACE_MODE_10GBASER)
  2086. rtl9300_sds_rxcal_leq_manual(sds_num, true, avg10);
  2087. }
  2088. }
  2089. }
  2090. pr_info("Sds:%u LEQ = %u",sds_num, rtl9300_sds_rxcal_leq_read(sds_num));
  2091. pr_info("end_1.3.2");
  2092. }
  2093. void rtl9300_do_rx_calibration_3(int sds_num, phy_interface_t phy_mode)
  2094. {
  2095. rtl9300_sds_rxcal_3_1(sds_num, phy_mode);
  2096. if (phy_mode == PHY_INTERFACE_MODE_10GBASER || phy_mode == PHY_INTERFACE_MODE_1000BASEX)
  2097. rtl9300_sds_rxcal_3_2(sds_num, phy_mode);
  2098. }
  2099. void rtl9300_do_rx_calibration_4_1(int sds_num)
  2100. {
  2101. u32 vth_list[2] = {0, 0};
  2102. u32 tap0_list[4] = {0, 0, 0, 0};
  2103. pr_info("start_1.4.1");
  2104. /* ##1.4.1 */
  2105. rtl9300_sds_rxcal_vth_manual(sds_num, false, vth_list);
  2106. rtl9300_sds_rxcal_tap_manual(sds_num, 0, false, tap0_list);
  2107. mdelay(200);
  2108. pr_info("end_1.4.1");
  2109. }
  2110. void rtl9300_do_rx_calibration_4_2(u32 sds_num)
  2111. {
  2112. u32 vth_list[2];
  2113. u32 tap_list[4];
  2114. pr_info("start_1.4.2");
  2115. rtl9300_sds_rxcal_vth_get(sds_num, vth_list);
  2116. rtl9300_sds_rxcal_vth_manual(sds_num, true, vth_list);
  2117. mdelay(100);
  2118. rtl9300_sds_rxcal_tap_get(sds_num, 0, tap_list);
  2119. rtl9300_sds_rxcal_tap_manual(sds_num, 0, true, tap_list);
  2120. pr_info("end_1.4.2");
  2121. }
  2122. void rtl9300_do_rx_calibration_4(u32 sds_num)
  2123. {
  2124. rtl9300_do_rx_calibration_4_1(sds_num);
  2125. rtl9300_do_rx_calibration_4_2(sds_num);
  2126. }
  2127. void rtl9300_do_rx_calibration_5_2(u32 sds_num)
  2128. {
  2129. u32 tap1_list[4] = {0};
  2130. u32 tap2_list[4] = {0};
  2131. u32 tap3_list[4] = {0};
  2132. u32 tap4_list[4] = {0};
  2133. pr_info("start_1.5.2");
  2134. rtl9300_sds_rxcal_tap_manual(sds_num, 1, false, tap1_list);
  2135. rtl9300_sds_rxcal_tap_manual(sds_num, 2, false, tap2_list);
  2136. rtl9300_sds_rxcal_tap_manual(sds_num, 3, false, tap3_list);
  2137. rtl9300_sds_rxcal_tap_manual(sds_num, 4, false, tap4_list);
  2138. mdelay(30);
  2139. pr_info("end_1.5.2");
  2140. }
  2141. void rtl9300_do_rx_calibration_5(u32 sds_num, phy_interface_t phy_mode)
  2142. {
  2143. if (phy_mode == PHY_INTERFACE_MODE_10GBASER) /* dfeTap1_4Enable true */
  2144. rtl9300_do_rx_calibration_5_2(sds_num);
  2145. }
  2146. void rtl9300_do_rx_calibration_dfe_disable(u32 sds_num)
  2147. {
  2148. u32 tap1_list[4] = {0};
  2149. u32 tap2_list[4] = {0};
  2150. u32 tap3_list[4] = {0};
  2151. u32 tap4_list[4] = {0};
  2152. rtl9300_sds_rxcal_tap_manual(sds_num, 1, true, tap1_list);
  2153. rtl9300_sds_rxcal_tap_manual(sds_num, 2, true, tap2_list);
  2154. rtl9300_sds_rxcal_tap_manual(sds_num, 3, true, tap3_list);
  2155. rtl9300_sds_rxcal_tap_manual(sds_num, 4, true, tap4_list);
  2156. mdelay(10);
  2157. }
  2158. void rtl9300_do_rx_calibration(int sds, phy_interface_t phy_mode)
  2159. {
  2160. u32 latch_sts;
  2161. rtl9300_do_rx_calibration_1(sds, phy_mode);
  2162. rtl9300_do_rx_calibration_2(sds);
  2163. rtl9300_do_rx_calibration_4(sds);
  2164. rtl9300_do_rx_calibration_5(sds, phy_mode);
  2165. mdelay(20);
  2166. /* Do this only for 10GR mode, SDS active in mode 0x1a */
  2167. if (rtl9300_sds_field_r(sds, 0x1f, 9, 11, 7) == RTL930X_SDS_MODE_10GBASER) {
  2168. pr_info("%s: SDS enabled\n", __func__);
  2169. latch_sts = rtl9300_sds_field_r(sds, 0x4, 1, 2, 2);
  2170. mdelay(1);
  2171. latch_sts = rtl9300_sds_field_r(sds, 0x4, 1, 2, 2);
  2172. if (latch_sts) {
  2173. rtl9300_do_rx_calibration_dfe_disable(sds);
  2174. rtl9300_do_rx_calibration_4(sds);
  2175. rtl9300_do_rx_calibration_5(sds, phy_mode);
  2176. }
  2177. }
  2178. }
  2179. int rtl9300_sds_sym_err_reset(int sds_num, phy_interface_t phy_mode)
  2180. {
  2181. switch (phy_mode) {
  2182. case PHY_INTERFACE_MODE_XGMII:
  2183. break;
  2184. case PHY_INTERFACE_MODE_10GBASER:
  2185. /* Read twice to clear */
  2186. rtl930x_read_sds_phy(sds_num, 5, 1);
  2187. rtl930x_read_sds_phy(sds_num, 5, 1);
  2188. break;
  2189. case PHY_INTERFACE_MODE_1000BASEX:
  2190. rtl9300_sds_field_w(sds_num, 0x1, 24, 2, 0, 0);
  2191. rtl9300_sds_field_w(sds_num, 0x1, 3, 15, 8, 0);
  2192. rtl9300_sds_field_w(sds_num, 0x1, 2, 15, 0, 0);
  2193. break;
  2194. default:
  2195. pr_info("%s unsupported phy mode\n", __func__);
  2196. return -1;
  2197. }
  2198. return 0;
  2199. }
  2200. u32 rtl9300_sds_sym_err_get(int sds_num, phy_interface_t phy_mode)
  2201. {
  2202. u32 v = 0;
  2203. switch (phy_mode) {
  2204. case PHY_INTERFACE_MODE_XGMII:
  2205. break;
  2206. case PHY_INTERFACE_MODE_1000BASEX:
  2207. case PHY_INTERFACE_MODE_10GBASER:
  2208. v = rtl930x_read_sds_phy(sds_num, 5, 1);
  2209. return v & 0xff;
  2210. default:
  2211. pr_info("%s unsupported PHY-mode\n", __func__);
  2212. }
  2213. return v;
  2214. }
  2215. int rtl9300_sds_check_calibration(int sds_num, phy_interface_t phy_mode)
  2216. {
  2217. u32 errors1, errors2;
  2218. rtl9300_sds_sym_err_reset(sds_num, phy_mode);
  2219. rtl9300_sds_sym_err_reset(sds_num, phy_mode);
  2220. /* Count errors during 1ms */
  2221. errors1 = rtl9300_sds_sym_err_get(sds_num, phy_mode);
  2222. mdelay(1);
  2223. errors2 = rtl9300_sds_sym_err_get(sds_num, phy_mode);
  2224. switch (phy_mode) {
  2225. case PHY_INTERFACE_MODE_1000BASEX:
  2226. case PHY_INTERFACE_MODE_XGMII:
  2227. if ((errors2 - errors1 > 100) ||
  2228. (errors1 >= 0xffff00) || (errors2 >= 0xffff00)) {
  2229. pr_info("%s XSGMII error rate too high\n", __func__);
  2230. return 1;
  2231. }
  2232. break;
  2233. case PHY_INTERFACE_MODE_10GBASER:
  2234. if (errors2 > 0) {
  2235. pr_info("%s 10GBASER error rate too high\n", __func__);
  2236. return 1;
  2237. }
  2238. break;
  2239. default:
  2240. return 1;
  2241. }
  2242. return 0;
  2243. }
  2244. void rtl9300_phy_enable_10g_1g(int sds_num)
  2245. {
  2246. u32 v;
  2247. /* Enable 1GBit PHY */
  2248. v = rtl930x_read_sds_phy(sds_num, PHY_PAGE_2, MII_BMCR);
  2249. pr_info("%s 1gbit phy: %08x\n", __func__, v);
  2250. v &= ~BMCR_PDOWN;
  2251. rtl930x_write_sds_phy(sds_num, PHY_PAGE_2, MII_BMCR, v);
  2252. pr_info("%s 1gbit phy enabled: %08x\n", __func__, v);
  2253. /* Enable 10GBit PHY */
  2254. v = rtl930x_read_sds_phy(sds_num, PHY_PAGE_4, MII_BMCR);
  2255. pr_info("%s 10gbit phy: %08x\n", __func__, v);
  2256. v &= ~BMCR_PDOWN;
  2257. rtl930x_write_sds_phy(sds_num, PHY_PAGE_4, MII_BMCR, v);
  2258. pr_info("%s 10gbit phy after: %08x\n", __func__, v);
  2259. /* dal_longan_construct_mac_default_10gmedia_fiber */
  2260. v = rtl930x_read_sds_phy(sds_num, 0x1f, 11);
  2261. pr_info("%s set medium: %08x\n", __func__, v);
  2262. v |= BIT(1);
  2263. rtl930x_write_sds_phy(sds_num, 0x1f, 11, v);
  2264. pr_info("%s set medium after: %08x\n", __func__, v);
  2265. }
  2266. static int rtl9300_sds_10g_idle(int sds_num);
  2267. static void rtl9300_serdes_patch(int sds_num);
  2268. #define RTL930X_MAC_FORCE_MODE_CTRL (0xCA1C)
  2269. int rtl9300_serdes_setup(int port, int sds_num, phy_interface_t phy_mode)
  2270. {
  2271. int calib_tries = 0;
  2272. /* Turn Off Serdes */
  2273. rtl9300_sds_rst(sds_num, RTL930X_SDS_OFF);
  2274. /* Apply serdes patches */
  2275. rtl9300_serdes_patch(sds_num);
  2276. /* Maybe use dal_longan_sds_init */
  2277. /* dal_longan_construct_serdesConfig_init */ /* Serdes Construct */
  2278. rtl9300_phy_enable_10g_1g(sds_num);
  2279. /* Disable MAC */
  2280. sw_w32_mask(0, 1, RTL930X_MAC_FORCE_MODE_CTRL + 4 * port);
  2281. mdelay(20);
  2282. /* ----> dal_longan_sds_mode_set */
  2283. pr_info("%s: Configuring RTL9300 SERDES %d\n", __func__, sds_num);
  2284. /* Configure link to MAC */
  2285. rtl9300_serdes_mac_link_config(sds_num, true, true); /* MAC Construct */
  2286. /* Re-Enable MAC */
  2287. sw_w32_mask(1, 0, RTL930X_MAC_FORCE_MODE_CTRL + 4 * port);
  2288. /* Enable SDS in desired mode */
  2289. rtl9300_force_sds_mode(sds_num, phy_mode);
  2290. /* Enable Fiber RX */
  2291. rtl9300_sds_field_w(sds_num, 0x20, 2, 12, 12, 0);
  2292. /* Calibrate SerDes receiver in loopback mode */
  2293. rtl9300_sds_10g_idle(sds_num);
  2294. do {
  2295. rtl9300_do_rx_calibration(sds_num, phy_mode);
  2296. calib_tries++;
  2297. mdelay(50);
  2298. } while (rtl9300_sds_check_calibration(sds_num, phy_mode) && calib_tries < 3);
  2299. if (calib_tries >= 3)
  2300. pr_warn("%s: SerDes RX calibration failed\n", __func__);
  2301. /* Leave loopback mode */
  2302. rtl9300_sds_tx_config(sds_num, phy_mode);
  2303. return 0;
  2304. }
  2305. static int rtl9300_sds_10g_idle(int sds_num)
  2306. {
  2307. bool busy;
  2308. int i = 0;
  2309. do {
  2310. if (sds_num % 2) {
  2311. rtl9300_sds_field_w(sds_num - 1, 0x1f, 0x2, 15, 0, 53);
  2312. busy = !!rtl9300_sds_field_r(sds_num - 1, 0x1f, 0x14, 1, 1);
  2313. } else {
  2314. rtl9300_sds_field_w(sds_num, 0x1f, 0x2, 15, 0, 53);
  2315. busy = !!rtl9300_sds_field_r(sds_num, 0x1f, 0x14, 0, 0);
  2316. }
  2317. i++;
  2318. } while (busy && i < 100);
  2319. if (i < 100)
  2320. return 0;
  2321. pr_warn("%s WARNING: Waiting for RX idle timed out, SDS %d\n", __func__, sds_num);
  2322. return -EIO;
  2323. }
  2324. typedef struct {
  2325. u8 page;
  2326. u8 reg;
  2327. u16 data;
  2328. } sds_config;
  2329. sds_config rtl9300_a_sds_10gr_lane0[] =
  2330. {
  2331. /* 1G */
  2332. {0x00, 0x0E, 0x3053}, {0x01, 0x14, 0x0100}, {0x21, 0x03, 0x8206},
  2333. {0x21, 0x05, 0x40B0}, {0x21, 0x06, 0x0010}, {0x21, 0x07, 0xF09F},
  2334. {0x21, 0x0C, 0x0007}, {0x21, 0x0D, 0x6009}, {0x21, 0x0E, 0x0000},
  2335. {0x21, 0x0F, 0x0008}, {0x24, 0x00, 0x0668}, {0x24, 0x02, 0xD020},
  2336. {0x24, 0x06, 0xC000}, {0x24, 0x0B, 0x1892}, {0x24, 0x0F, 0xFFDF},
  2337. {0x24, 0x12, 0x03C4}, {0x24, 0x13, 0x027F}, {0x24, 0x14, 0x1311},
  2338. {0x24, 0x16, 0x00C9}, {0x24, 0x17, 0xA100}, {0x24, 0x1A, 0x0001},
  2339. {0x24, 0x1C, 0x0400}, {0x25, 0x01, 0x0300}, {0x25, 0x02, 0x1017},
  2340. {0x25, 0x03, 0xFFDF}, {0x25, 0x05, 0x7F7C}, {0x25, 0x07, 0x8100},
  2341. {0x25, 0x08, 0x0001}, {0x25, 0x09, 0xFFD4}, {0x25, 0x0A, 0x7C2F},
  2342. {0x25, 0x0E, 0x003F}, {0x25, 0x0F, 0x0121}, {0x25, 0x10, 0x0020},
  2343. {0x25, 0x11, 0x8840}, {0x2B, 0x13, 0x0050}, {0x2B, 0x18, 0x8E88},
  2344. {0x2B, 0x19, 0x4902}, {0x2B, 0x1D, 0x2501}, {0x2D, 0x13, 0x0050},
  2345. {0x2D, 0x18, 0x8E88}, {0x2D, 0x19, 0x4902}, {0x2D, 0x1D, 0x2641},
  2346. {0x2F, 0x13, 0x0050}, {0x2F, 0x18, 0x8E88}, {0x2F, 0x19, 0x4902},
  2347. {0x2F, 0x1D, 0x66E1},
  2348. /* 3.125G */
  2349. {0x28, 0x00, 0x0668}, {0x28, 0x02, 0xD020}, {0x28, 0x06, 0xC000},
  2350. {0x28, 0x0B, 0x1892}, {0x28, 0x0F, 0xFFDF}, {0x28, 0x12, 0x01C4},
  2351. {0x28, 0x13, 0x027F}, {0x28, 0x14, 0x1311}, {0x28, 0x16, 0x00C9},
  2352. {0x28, 0x17, 0xA100}, {0x28, 0x1A, 0x0001}, {0x28, 0x1C, 0x0400},
  2353. {0x29, 0x01, 0x0300}, {0x29, 0x02, 0x1017}, {0x29, 0x03, 0xFFDF},
  2354. {0x29, 0x05, 0x7F7C}, {0x29, 0x07, 0x8100}, {0x29, 0x08, 0x0001},
  2355. {0x29, 0x09, 0xFFD4}, {0x29, 0x0A, 0x7C2F}, {0x29, 0x0E, 0x003F},
  2356. {0x29, 0x0F, 0x0121}, {0x29, 0x10, 0x0020}, {0x29, 0x11, 0x8840},
  2357. /* 10G */
  2358. {0x06, 0x0D, 0x0F00}, {0x06, 0x00, 0x0000}, {0x06, 0x01, 0xC800},
  2359. {0x21, 0x03, 0x8206}, {0x21, 0x05, 0x40B0}, {0x21, 0x06, 0x0010},
  2360. {0x21, 0x07, 0xF09F}, {0x21, 0x0C, 0x0007}, {0x21, 0x0D, 0x6009},
  2361. {0x21, 0x0E, 0x0000}, {0x21, 0x0F, 0x0008}, {0x2E, 0x00, 0xA668},
  2362. {0x2E, 0x02, 0xD020}, {0x2E, 0x06, 0xC000}, {0x2E, 0x0B, 0x1892},
  2363. {0x2E, 0x0F, 0xFFDF}, {0x2E, 0x11, 0x8280}, {0x2E, 0x12, 0x0044},
  2364. {0x2E, 0x13, 0x027F}, {0x2E, 0x14, 0x1311}, {0x2E, 0x17, 0xA100},
  2365. {0x2E, 0x1A, 0x0001}, {0x2E, 0x1C, 0x0400}, {0x2F, 0x01, 0x0300},
  2366. {0x2F, 0x02, 0x1217}, {0x2F, 0x03, 0xFFDF}, {0x2F, 0x05, 0x7F7C},
  2367. {0x2F, 0x07, 0x80C4}, {0x2F, 0x08, 0x0001}, {0x2F, 0x09, 0xFFD4},
  2368. {0x2F, 0x0A, 0x7C2F}, {0x2F, 0x0E, 0x003F}, {0x2F, 0x0F, 0x0121},
  2369. {0x2F, 0x10, 0x0020}, {0x2F, 0x11, 0x8840}, {0x2F, 0x14, 0xE008},
  2370. {0x2B, 0x13, 0x0050}, {0x2B, 0x18, 0x8E88}, {0x2B, 0x19, 0x4902},
  2371. {0x2B, 0x1D, 0x2501}, {0x2D, 0x13, 0x0050}, {0x2D, 0x17, 0x4109},
  2372. {0x2D, 0x18, 0x8E88}, {0x2D, 0x19, 0x4902}, {0x2D, 0x1C, 0x1109},
  2373. {0x2D, 0x1D, 0x2641}, {0x2F, 0x13, 0x0050}, {0x2F, 0x18, 0x8E88},
  2374. {0x2F, 0x19, 0x4902}, {0x2F, 0x1D, 0x76E1},
  2375. };
  2376. sds_config rtl9300_a_sds_10gr_lane1[] =
  2377. {
  2378. /* 1G */
  2379. {0x00, 0x0E, 0x3053}, {0x01, 0x14, 0x0100}, {0x21, 0x03, 0x8206},
  2380. {0x21, 0x06, 0x0010}, {0x21, 0x07, 0xF09F}, {0x21, 0x0A, 0x0003},
  2381. {0x21, 0x0B, 0x0005}, {0x21, 0x0C, 0x0007}, {0x21, 0x0D, 0x6009},
  2382. {0x21, 0x0E, 0x0000}, {0x21, 0x0F, 0x0008}, {0x24, 0x00, 0x0668},
  2383. {0x24, 0x02, 0xD020}, {0x24, 0x06, 0xC000}, {0x24, 0x0B, 0x1892},
  2384. {0x24, 0x0F, 0xFFDF}, {0x24, 0x12, 0x03C4}, {0x24, 0x13, 0x027F},
  2385. {0x24, 0x14, 0x1311}, {0x24, 0x16, 0x00C9}, {0x24, 0x17, 0xA100},
  2386. {0x24, 0x1A, 0x0001}, {0x24, 0x1C, 0x0400}, {0x25, 0x00, 0x820F},
  2387. {0x25, 0x01, 0x0300}, {0x25, 0x02, 0x1017}, {0x25, 0x03, 0xFFDF},
  2388. {0x25, 0x05, 0x7F7C}, {0x25, 0x07, 0x8100}, {0x25, 0x08, 0x0001},
  2389. {0x25, 0x09, 0xFFD4}, {0x25, 0x0A, 0x7C2F}, {0x25, 0x0E, 0x003F},
  2390. {0x25, 0x0F, 0x0121}, {0x25, 0x10, 0x0020}, {0x25, 0x11, 0x8840},
  2391. {0x2B, 0x13, 0x3D87}, {0x2B, 0x14, 0x3108}, {0x2D, 0x13, 0x3C87},
  2392. {0x2D, 0x14, 0x1808},
  2393. /* 3.125G */
  2394. {0x28, 0x00, 0x0668}, {0x28, 0x02, 0xD020}, {0x28, 0x06, 0xC000},
  2395. {0x28, 0x0B, 0x1892}, {0x28, 0x0F, 0xFFDF}, {0x28, 0x12, 0x01C4},
  2396. {0x28, 0x13, 0x027F}, {0x28, 0x14, 0x1311}, {0x28, 0x16, 0x00C9},
  2397. {0x28, 0x17, 0xA100}, {0x28, 0x1A, 0x0001}, {0x28, 0x1C, 0x0400},
  2398. {0x29, 0x00, 0x820F}, {0x29, 0x01, 0x0300}, {0x29, 0x02, 0x1017},
  2399. {0x29, 0x03, 0xFFDF}, {0x29, 0x05, 0x7F7C}, {0x29, 0x07, 0x8100},
  2400. {0x29, 0x08, 0x0001}, {0x29, 0x0A, 0x7C2F}, {0x29, 0x0E, 0x003F},
  2401. {0x29, 0x0F, 0x0121}, {0x29, 0x10, 0x0020}, {0x29, 0x11, 0x8840},
  2402. /* 10G */
  2403. {0x06, 0x0D, 0x0F00}, {0x06, 0x00, 0x0000}, {0x06, 0x01, 0xC800},
  2404. {0x21, 0x03, 0x8206}, {0x21, 0x05, 0x40B0}, {0x21, 0x06, 0x0010},
  2405. {0x21, 0x07, 0xF09F}, {0x21, 0x0A, 0x0003}, {0x21, 0x0B, 0x0005},
  2406. {0x21, 0x0C, 0x0007}, {0x21, 0x0D, 0x6009}, {0x21, 0x0E, 0x0000},
  2407. {0x21, 0x0F, 0x0008}, {0x2E, 0x00, 0xA668}, {0x2E, 0x02, 0xD020},
  2408. {0x2E, 0x06, 0xC000}, {0x2E, 0x0B, 0x1892}, {0x2E, 0x0F, 0xFFDF},
  2409. {0x2E, 0x11, 0x8280}, {0x2E, 0x12, 0x0044}, {0x2E, 0x13, 0x027F},
  2410. {0x2E, 0x14, 0x1311}, {0x2E, 0x17, 0xA100}, {0x2E, 0x1A, 0x0001},
  2411. {0x2E, 0x1C, 0x0400}, {0x2F, 0x00, 0x820F}, {0x2F, 0x01, 0x0300},
  2412. {0x2F, 0x02, 0x1217}, {0x2F, 0x03, 0xFFDF}, {0x2F, 0x05, 0x7F7C},
  2413. {0x2F, 0x07, 0x80C4}, {0x2F, 0x08, 0x0001}, {0x2F, 0x09, 0xFFD4},
  2414. {0x2F, 0x0A, 0x7C2F}, {0x2F, 0x0E, 0x003F}, {0x2F, 0x0F, 0x0121},
  2415. {0x2F, 0x10, 0x0020}, {0x2F, 0x11, 0x8840}, {0x2B, 0x13, 0x3D87},
  2416. {0x2B, 0x14, 0x3108}, {0x2D, 0x13, 0x3C87}, {0x2D, 0x14, 0x1808},
  2417. };
  2418. static void rtl9300_serdes_patch(int sds_num)
  2419. {
  2420. if (sds_num % 2) {
  2421. for (int i = 0; i < sizeof(rtl9300_a_sds_10gr_lane1) / sizeof(sds_config); ++i) {
  2422. rtl930x_write_sds_phy(sds_num, rtl9300_a_sds_10gr_lane1[i].page,
  2423. rtl9300_a_sds_10gr_lane1[i].reg,
  2424. rtl9300_a_sds_10gr_lane1[i].data);
  2425. }
  2426. } else {
  2427. for (int i = 0; i < sizeof(rtl9300_a_sds_10gr_lane0) / sizeof(sds_config); ++i) {
  2428. rtl930x_write_sds_phy(sds_num, rtl9300_a_sds_10gr_lane0[i].page,
  2429. rtl9300_a_sds_10gr_lane0[i].reg,
  2430. rtl9300_a_sds_10gr_lane0[i].data);
  2431. }
  2432. }
  2433. }
  2434. int rtl9300_sds_cmu_band_get(int sds)
  2435. {
  2436. u32 page;
  2437. u32 en;
  2438. u32 cmu_band;
  2439. /* page = rtl9300_sds_cmu_page_get(sds); */
  2440. page = 0x25; /* 10GR and 1000BX */
  2441. sds = (sds % 2) ? (sds - 1) : (sds);
  2442. rtl9300_sds_field_w(sds, page, 0x1c, 15, 15, 1);
  2443. rtl9300_sds_field_w(sds + 1, page, 0x1c, 15, 15, 1);
  2444. en = rtl9300_sds_field_r(sds, page, 27, 1, 1);
  2445. if(!en) { /* Auto mode */
  2446. rtl930x_write_sds_phy(sds, 0x1f, 0x02, 31);
  2447. cmu_band = rtl9300_sds_field_r(sds, 0x1f, 0x15, 5, 1);
  2448. } else {
  2449. cmu_band = rtl9300_sds_field_r(sds, page, 30, 4, 0);
  2450. }
  2451. return cmu_band;
  2452. }
  2453. void rtl9310_sds_field_w(int sds, u32 page, u32 reg, int end_bit, int start_bit, u32 v)
  2454. {
  2455. int l = end_bit - start_bit + 1;
  2456. u32 data = v;
  2457. if (l < 32) {
  2458. u32 mask = BIT(l) - 1;
  2459. data = rtl930x_read_sds_phy(sds, page, reg);
  2460. data &= ~(mask << start_bit);
  2461. data |= (v & mask) << start_bit;
  2462. }
  2463. rtl931x_write_sds_phy(sds, page, reg, data);
  2464. }
  2465. u32 rtl9310_sds_field_r(int sds, u32 page, u32 reg, int end_bit, int start_bit)
  2466. {
  2467. int l = end_bit - start_bit + 1;
  2468. u32 v = rtl931x_read_sds_phy(sds, page, reg);
  2469. if (l >= 32)
  2470. return v;
  2471. return (v >> start_bit) & (BIT(l) - 1);
  2472. }
  2473. static void rtl931x_sds_rst(u32 sds)
  2474. {
  2475. u32 o, v, o_mode;
  2476. int shift = ((sds & 0x3) << 3);
  2477. /* TODO: We need to lock this! */
  2478. o = sw_r32(RTL931X_PS_SERDES_OFF_MODE_CTRL_ADDR);
  2479. v = o | BIT(sds);
  2480. sw_w32(v, RTL931X_PS_SERDES_OFF_MODE_CTRL_ADDR);
  2481. o_mode = sw_r32(RTL931X_SERDES_MODE_CTRL + 4 * (sds >> 2));
  2482. v = BIT(7) | 0x1F;
  2483. sw_w32_mask(0xff << shift, v << shift, RTL931X_SERDES_MODE_CTRL + 4 * (sds >> 2));
  2484. sw_w32(o_mode, RTL931X_SERDES_MODE_CTRL + 4 * (sds >> 2));
  2485. sw_w32(o, RTL931X_PS_SERDES_OFF_MODE_CTRL_ADDR);
  2486. }
  2487. static void rtl931x_symerr_clear(u32 sds, phy_interface_t mode)
  2488. {
  2489. switch (mode) {
  2490. case PHY_INTERFACE_MODE_NA:
  2491. break;
  2492. case PHY_INTERFACE_MODE_XGMII:
  2493. u32 xsg_sdsid_0, xsg_sdsid_1;
  2494. if (sds < 2)
  2495. xsg_sdsid_0 = sds;
  2496. else
  2497. xsg_sdsid_0 = (sds - 1) * 2;
  2498. xsg_sdsid_1 = xsg_sdsid_0 + 1;
  2499. for (int i = 0; i < 4; ++i) {
  2500. rtl9310_sds_field_w(xsg_sdsid_0, 0x1, 24, 2, 0, i);
  2501. rtl9310_sds_field_w(xsg_sdsid_0, 0x1, 3, 15, 8, 0x0);
  2502. rtl9310_sds_field_w(xsg_sdsid_0, 0x1, 2, 15, 0, 0x0);
  2503. }
  2504. for (int i = 0; i < 4; ++i) {
  2505. rtl9310_sds_field_w(xsg_sdsid_1, 0x1, 24, 2, 0, i);
  2506. rtl9310_sds_field_w(xsg_sdsid_1, 0x1, 3, 15, 8, 0x0);
  2507. rtl9310_sds_field_w(xsg_sdsid_1, 0x1, 2, 15, 0, 0x0);
  2508. }
  2509. rtl9310_sds_field_w(xsg_sdsid_0, 0x1, 0, 15, 0, 0x0);
  2510. rtl9310_sds_field_w(xsg_sdsid_0, 0x1, 1, 15, 8, 0x0);
  2511. rtl9310_sds_field_w(xsg_sdsid_1, 0x1, 0, 15, 0, 0x0);
  2512. rtl9310_sds_field_w(xsg_sdsid_1, 0x1, 1, 15, 8, 0x0);
  2513. break;
  2514. default:
  2515. break;
  2516. }
  2517. return;
  2518. }
  2519. static u32 rtl931x_get_analog_sds(u32 sds)
  2520. {
  2521. u32 sds_map[] = { 0, 1, 2, 3, 6, 7, 10, 11, 14, 15, 18, 19, 22, 23 };
  2522. if (sds < 14)
  2523. return sds_map[sds];
  2524. return sds;
  2525. }
  2526. void rtl931x_sds_fiber_disable(u32 sds)
  2527. {
  2528. u32 v = 0x3F;
  2529. u32 asds = rtl931x_get_analog_sds(sds);
  2530. rtl9310_sds_field_w(asds, 0x1F, 0x9, 11, 6, v);
  2531. }
  2532. static void rtl931x_sds_fiber_mode_set(u32 sds, phy_interface_t mode)
  2533. {
  2534. u32 val, asds = rtl931x_get_analog_sds(sds);
  2535. /* clear symbol error count before changing mode */
  2536. rtl931x_symerr_clear(sds, mode);
  2537. val = 0x9F;
  2538. sw_w32(val, RTL931X_SERDES_MODE_CTRL + 4 * (sds >> 2));
  2539. switch (mode) {
  2540. case PHY_INTERFACE_MODE_SGMII:
  2541. val = 0x5;
  2542. break;
  2543. case PHY_INTERFACE_MODE_1000BASEX:
  2544. /* serdes mode FIBER1G */
  2545. val = 0x9;
  2546. break;
  2547. case PHY_INTERFACE_MODE_10GBASER:
  2548. case PHY_INTERFACE_MODE_10GKR:
  2549. val = 0x35;
  2550. break;
  2551. /* case MII_10GR1000BX_AUTO:
  2552. val = 0x39;
  2553. break; */
  2554. case PHY_INTERFACE_MODE_USXGMII:
  2555. val = 0x1B;
  2556. break;
  2557. default:
  2558. val = 0x25;
  2559. }
  2560. pr_info("%s writing analog SerDes Mode value %02x\n", __func__, val);
  2561. rtl9310_sds_field_w(asds, 0x1F, 0x9, 11, 6, val);
  2562. return;
  2563. }
  2564. static int rtl931x_sds_cmu_page_get(phy_interface_t mode)
  2565. {
  2566. switch (mode) {
  2567. case PHY_INTERFACE_MODE_SGMII:
  2568. case PHY_INTERFACE_MODE_1000BASEX: /* MII_1000BX_FIBER / 100BX_FIBER / 1000BX100BX_AUTO */
  2569. return 0x24;
  2570. case PHY_INTERFACE_MODE_HSGMII:
  2571. case PHY_INTERFACE_MODE_2500BASEX: /* MII_2500Base_X: */
  2572. return 0x28;
  2573. /* case MII_HISGMII_5G: */
  2574. /* return 0x2a; */
  2575. case PHY_INTERFACE_MODE_QSGMII:
  2576. return 0x2a; /* Code also has 0x34 */
  2577. case PHY_INTERFACE_MODE_XAUI: /* MII_RXAUI_LITE: */
  2578. return 0x2c;
  2579. case PHY_INTERFACE_MODE_XGMII: /* MII_XSGMII */
  2580. case PHY_INTERFACE_MODE_10GKR:
  2581. case PHY_INTERFACE_MODE_10GBASER: /* MII_10GR */
  2582. return 0x2e;
  2583. default:
  2584. return -1;
  2585. }
  2586. return -1;
  2587. }
  2588. static void rtl931x_cmu_type_set(u32 asds, phy_interface_t mode, int chiptype)
  2589. {
  2590. int cmu_type = 0; /* Clock Management Unit */
  2591. u32 cmu_page = 0;
  2592. u32 frc_cmu_spd;
  2593. u32 evenSds;
  2594. u32 lane, frc_lc_mode_bitnum, frc_lc_mode_val_bitnum;
  2595. switch (mode) {
  2596. case PHY_INTERFACE_MODE_NA:
  2597. case PHY_INTERFACE_MODE_10GKR:
  2598. case PHY_INTERFACE_MODE_XGMII:
  2599. case PHY_INTERFACE_MODE_10GBASER:
  2600. case PHY_INTERFACE_MODE_USXGMII:
  2601. return;
  2602. /* case MII_10GR1000BX_AUTO:
  2603. if (chiptype)
  2604. rtl9310_sds_field_w(asds, 0x24, 0xd, 14, 14, 0);
  2605. return; */
  2606. case PHY_INTERFACE_MODE_QSGMII:
  2607. cmu_type = 1;
  2608. frc_cmu_spd = 0;
  2609. break;
  2610. case PHY_INTERFACE_MODE_HSGMII:
  2611. cmu_type = 1;
  2612. frc_cmu_spd = 1;
  2613. break;
  2614. case PHY_INTERFACE_MODE_1000BASEX:
  2615. cmu_type = 1;
  2616. frc_cmu_spd = 0;
  2617. break;
  2618. /* case MII_1000BX100BX_AUTO:
  2619. cmu_type = 1;
  2620. frc_cmu_spd = 0;
  2621. break; */
  2622. case PHY_INTERFACE_MODE_SGMII:
  2623. cmu_type = 1;
  2624. frc_cmu_spd = 0;
  2625. break;
  2626. case PHY_INTERFACE_MODE_2500BASEX:
  2627. cmu_type = 1;
  2628. frc_cmu_spd = 1;
  2629. break;
  2630. default:
  2631. pr_info("SerDes %d mode is invalid\n", asds);
  2632. return;
  2633. }
  2634. if (cmu_type == 1)
  2635. cmu_page = rtl931x_sds_cmu_page_get(mode);
  2636. lane = asds % 2;
  2637. if (!lane) {
  2638. frc_lc_mode_bitnum = 4;
  2639. frc_lc_mode_val_bitnum = 5;
  2640. } else {
  2641. frc_lc_mode_bitnum = 6;
  2642. frc_lc_mode_val_bitnum = 7;
  2643. }
  2644. evenSds = asds - lane;
  2645. pr_info("%s: cmu_type %0d cmu_page %x frc_cmu_spd %d lane %d asds %d\n",
  2646. __func__, cmu_type, cmu_page, frc_cmu_spd, lane, asds);
  2647. if (cmu_type == 1) {
  2648. pr_info("%s A CMU page 0x28 0x7 %08x\n", __func__, rtl931x_read_sds_phy(asds, 0x28, 0x7));
  2649. rtl9310_sds_field_w(asds, cmu_page, 0x7, 15, 15, 0);
  2650. pr_info("%s B CMU page 0x28 0x7 %08x\n", __func__, rtl931x_read_sds_phy(asds, 0x28, 0x7));
  2651. if (chiptype) {
  2652. rtl9310_sds_field_w(asds, cmu_page, 0xd, 14, 14, 0);
  2653. }
  2654. rtl9310_sds_field_w(evenSds, 0x20, 0x12, 3, 2, 0x3);
  2655. rtl9310_sds_field_w(evenSds, 0x20, 0x12, frc_lc_mode_bitnum, frc_lc_mode_bitnum, 1);
  2656. rtl9310_sds_field_w(evenSds, 0x20, 0x12, frc_lc_mode_val_bitnum, frc_lc_mode_val_bitnum, 0);
  2657. rtl9310_sds_field_w(evenSds, 0x20, 0x12, 12, 12, 1);
  2658. rtl9310_sds_field_w(evenSds, 0x20, 0x12, 15, 13, frc_cmu_spd);
  2659. }
  2660. pr_info("%s CMU page 0x28 0x7 %08x\n", __func__, rtl931x_read_sds_phy(asds, 0x28, 0x7));
  2661. return;
  2662. }
  2663. static void rtl931x_sds_rx_rst(u32 sds)
  2664. {
  2665. u32 asds = rtl931x_get_analog_sds(sds);
  2666. if (sds < 2)
  2667. return;
  2668. rtl931x_write_sds_phy(asds, 0x2e, 0x12, 0x2740);
  2669. rtl931x_write_sds_phy(asds, 0x2f, 0x0, 0x0);
  2670. rtl931x_write_sds_phy(asds, 0x2f, 0x2, 0x2010);
  2671. rtl931x_write_sds_phy(asds, 0x20, 0x0, 0xc10);
  2672. rtl931x_write_sds_phy(asds, 0x2e, 0x12, 0x27c0);
  2673. rtl931x_write_sds_phy(asds, 0x2f, 0x0, 0xc000);
  2674. rtl931x_write_sds_phy(asds, 0x2f, 0x2, 0x6010);
  2675. rtl931x_write_sds_phy(asds, 0x20, 0x0, 0xc30);
  2676. mdelay(50);
  2677. }
  2678. // Currently not used
  2679. // static void rtl931x_sds_disable(u32 sds)
  2680. // {
  2681. // u32 v = 0x1f;
  2682. // v |= BIT(7);
  2683. // sw_w32(v, RTL931X_SERDES_MODE_CTRL + (sds >> 2) * 4);
  2684. // }
  2685. static void rtl931x_sds_mii_mode_set(u32 sds, phy_interface_t mode)
  2686. {
  2687. u32 val;
  2688. switch (mode) {
  2689. case PHY_INTERFACE_MODE_QSGMII:
  2690. val = 0x6;
  2691. break;
  2692. case PHY_INTERFACE_MODE_XGMII:
  2693. val = 0x10; /* serdes mode XSGMII */
  2694. break;
  2695. case PHY_INTERFACE_MODE_USXGMII:
  2696. case PHY_INTERFACE_MODE_2500BASEX:
  2697. val = 0xD;
  2698. break;
  2699. case PHY_INTERFACE_MODE_HSGMII:
  2700. val = 0x12;
  2701. break;
  2702. case PHY_INTERFACE_MODE_SGMII:
  2703. val = 0x2;
  2704. break;
  2705. default:
  2706. return;
  2707. }
  2708. val |= (1 << 7);
  2709. sw_w32(val, RTL931X_SERDES_MODE_CTRL + 4 * (sds >> 2));
  2710. }
  2711. static sds_config sds_config_10p3125g_type1[] = {
  2712. { 0x2E, 0x00, 0x0107 }, { 0x2E, 0x01, 0x01A3 }, { 0x2E, 0x02, 0x6A24 },
  2713. { 0x2E, 0x03, 0xD10D }, { 0x2E, 0x04, 0x8000 }, { 0x2E, 0x05, 0xA17E },
  2714. { 0x2E, 0x06, 0xE31D }, { 0x2E, 0x07, 0x800E }, { 0x2E, 0x08, 0x0294 },
  2715. { 0x2E, 0x09, 0x0CE4 }, { 0x2E, 0x0A, 0x7FC8 }, { 0x2E, 0x0B, 0xE0E7 },
  2716. { 0x2E, 0x0C, 0x0200 }, { 0x2E, 0x0D, 0xDF80 }, { 0x2E, 0x0E, 0x0000 },
  2717. { 0x2E, 0x0F, 0x1FC2 }, { 0x2E, 0x10, 0x0C3F }, { 0x2E, 0x11, 0x0000 },
  2718. { 0x2E, 0x12, 0x27C0 }, { 0x2E, 0x13, 0x7E1D }, { 0x2E, 0x14, 0x1300 },
  2719. { 0x2E, 0x15, 0x003F }, { 0x2E, 0x16, 0xBE7F }, { 0x2E, 0x17, 0x0090 },
  2720. { 0x2E, 0x18, 0x0000 }, { 0x2E, 0x19, 0x4000 }, { 0x2E, 0x1A, 0x0000 },
  2721. { 0x2E, 0x1B, 0x8000 }, { 0x2E, 0x1C, 0x011F }, { 0x2E, 0x1D, 0x0000 },
  2722. { 0x2E, 0x1E, 0xC8FF }, { 0x2E, 0x1F, 0x0000 }, { 0x2F, 0x00, 0xC000 },
  2723. { 0x2F, 0x01, 0xF000 }, { 0x2F, 0x02, 0x6010 }, { 0x2F, 0x12, 0x0EE7 },
  2724. { 0x2F, 0x13, 0x0000 }
  2725. };
  2726. static sds_config sds_config_10p3125g_cmu_type1[] = {
  2727. { 0x2F, 0x03, 0x4210 }, { 0x2F, 0x04, 0x0000 }, { 0x2F, 0x05, 0x0019 },
  2728. { 0x2F, 0x06, 0x18A6 }, { 0x2F, 0x07, 0x2990 }, { 0x2F, 0x08, 0xFFF4 },
  2729. { 0x2F, 0x09, 0x1F08 }, { 0x2F, 0x0A, 0x0000 }, { 0x2F, 0x0B, 0x8000 },
  2730. { 0x2F, 0x0C, 0x4224 }, { 0x2F, 0x0D, 0x0000 }, { 0x2F, 0x0E, 0x0000 },
  2731. { 0x2F, 0x0F, 0xA470 }, { 0x2F, 0x10, 0x8000 }, { 0x2F, 0x11, 0x037B }
  2732. };
  2733. void rtl931x_sds_init(u32 sds, phy_interface_t mode)
  2734. {
  2735. u32 board_sds_tx_type1[] = {
  2736. 0x01c3, 0x01c3, 0x01c3, 0x01a3, 0x01a3, 0x01a3,
  2737. 0x0143, 0x0143, 0x0143, 0x0143, 0x0163, 0x0163,
  2738. };
  2739. u32 board_sds_tx[] = {
  2740. 0x1a00, 0x1a00, 0x0200, 0x0200, 0x0200, 0x0200,
  2741. 0x01a3, 0x01a3, 0x01a3, 0x01a3, 0x01e3, 0x01e3
  2742. };
  2743. u32 board_sds_tx2[] = {
  2744. 0x0dc0, 0x01c0, 0x0200, 0x0180, 0x0160, 0x0123,
  2745. 0x0123, 0x0163, 0x01a3, 0x01a0, 0x01c3, 0x09c3,
  2746. };
  2747. u32 asds, dSds, ori, model_info, val;
  2748. int chiptype = 0;
  2749. asds = rtl931x_get_analog_sds(sds);
  2750. if (sds > 13)
  2751. return;
  2752. pr_info("%s: set sds %d to mode %d\n", __func__, sds, mode);
  2753. val = rtl9310_sds_field_r(asds, 0x1F, 0x9, 11, 6);
  2754. pr_info("%s: fibermode %08X stored mode 0x%x analog SDS %d", __func__,
  2755. rtl931x_read_sds_phy(asds, 0x1f, 0x9), val, asds);
  2756. pr_info("%s: SGMII mode %08X in 0x24 0x9 analog SDS %d", __func__,
  2757. rtl931x_read_sds_phy(asds, 0x24, 0x9), asds);
  2758. pr_info("%s: CMU mode %08X stored even SDS %d", __func__,
  2759. rtl931x_read_sds_phy(asds & ~1, 0x20, 0x12), asds & ~1);
  2760. pr_info("%s: serdes_mode_ctrl %08X", __func__, RTL931X_SERDES_MODE_CTRL + 4 * (sds >> 2));
  2761. pr_info("%s CMU page 0x24 0x7 %08x\n", __func__, rtl931x_read_sds_phy(asds, 0x24, 0x7));
  2762. pr_info("%s CMU page 0x26 0x7 %08x\n", __func__, rtl931x_read_sds_phy(asds, 0x26, 0x7));
  2763. pr_info("%s CMU page 0x28 0x7 %08x\n", __func__, rtl931x_read_sds_phy(asds, 0x28, 0x7));
  2764. pr_info("%s XSG page 0x0 0xe %08x\n", __func__, rtl931x_read_sds_phy(dSds, 0x0, 0xe));
  2765. pr_info("%s XSG2 page 0x0 0xe %08x\n", __func__, rtl931x_read_sds_phy(dSds + 1, 0x0, 0xe));
  2766. model_info = sw_r32(RTL93XX_MODEL_NAME_INFO);
  2767. if ((model_info >> 4) & 0x1) {
  2768. pr_info("detected chiptype 1\n");
  2769. chiptype = 1;
  2770. } else {
  2771. pr_info("detected chiptype 0\n");
  2772. }
  2773. if (sds < 2)
  2774. dSds = sds;
  2775. else
  2776. dSds = (sds - 1) * 2;
  2777. pr_info("%s: 2.5gbit %08X dsds %d", __func__,
  2778. rtl931x_read_sds_phy(dSds, 0x1, 0x14), dSds);
  2779. pr_info("%s: RTL931X_PS_SERDES_OFF_MODE_CTRL_ADDR 0x%08X\n", __func__, sw_r32(RTL931X_PS_SERDES_OFF_MODE_CTRL_ADDR));
  2780. ori = sw_r32(RTL931X_PS_SERDES_OFF_MODE_CTRL_ADDR);
  2781. val = ori | (1 << sds);
  2782. sw_w32(val, RTL931X_PS_SERDES_OFF_MODE_CTRL_ADDR);
  2783. switch (mode) {
  2784. case PHY_INTERFACE_MODE_NA:
  2785. break;
  2786. case PHY_INTERFACE_MODE_XGMII: /* MII_XSGMII */
  2787. if (chiptype) {
  2788. u32 xsg_sdsid_1;
  2789. xsg_sdsid_1 = dSds + 1;
  2790. /* fifo inv clk */
  2791. rtl9310_sds_field_w(dSds, 0x1, 0x1, 7, 4, 0xf);
  2792. rtl9310_sds_field_w(dSds, 0x1, 0x1, 3, 0, 0xf);
  2793. rtl9310_sds_field_w(xsg_sdsid_1, 0x1, 0x1, 7, 4, 0xf);
  2794. rtl9310_sds_field_w(xsg_sdsid_1, 0x1, 0x1, 3, 0, 0xf);
  2795. }
  2796. rtl9310_sds_field_w(dSds, 0x0, 0xE, 12, 12, 1);
  2797. rtl9310_sds_field_w(dSds + 1, 0x0, 0xE, 12, 12, 1);
  2798. break;
  2799. case PHY_INTERFACE_MODE_USXGMII: /* MII_USXGMII_10GSXGMII/10GDXGMII/10GQXGMII: */
  2800. u32 op_code = 0x6003;
  2801. u32 evenSds;
  2802. if (chiptype) {
  2803. rtl9310_sds_field_w(asds, 0x6, 0x2, 12, 12, 1);
  2804. for (int i = 0; i < sizeof(sds_config_10p3125g_type1) / sizeof(sds_config); ++i) {
  2805. rtl931x_write_sds_phy(asds, sds_config_10p3125g_type1[i].page - 0x4, sds_config_10p3125g_type1[i].reg, sds_config_10p3125g_type1[i].data);
  2806. }
  2807. evenSds = asds - (asds % 2);
  2808. for (int i = 0; i < sizeof(sds_config_10p3125g_cmu_type1) / sizeof(sds_config); ++i) {
  2809. rtl931x_write_sds_phy(evenSds,
  2810. sds_config_10p3125g_cmu_type1[i].page - 0x4, sds_config_10p3125g_cmu_type1[i].reg, sds_config_10p3125g_cmu_type1[i].data);
  2811. }
  2812. rtl9310_sds_field_w(asds, 0x6, 0x2, 12, 12, 0);
  2813. } else {
  2814. rtl9310_sds_field_w(asds, 0x2e, 0xd, 6, 0, 0x0);
  2815. rtl9310_sds_field_w(asds, 0x2e, 0xd, 7, 7, 0x1);
  2816. rtl9310_sds_field_w(asds, 0x2e, 0x1c, 5, 0, 0x1E);
  2817. rtl9310_sds_field_w(asds, 0x2e, 0x1d, 11, 0, 0x00);
  2818. rtl9310_sds_field_w(asds, 0x2e, 0x1f, 11, 0, 0x00);
  2819. rtl9310_sds_field_w(asds, 0x2f, 0x0, 11, 0, 0x00);
  2820. rtl9310_sds_field_w(asds, 0x2f, 0x1, 11, 0, 0x00);
  2821. rtl9310_sds_field_w(asds, 0x2e, 0xf, 12, 6, 0x7F);
  2822. rtl931x_write_sds_phy(asds, 0x2f, 0x12, 0xaaa);
  2823. rtl931x_sds_rx_rst(sds);
  2824. rtl931x_write_sds_phy(asds, 0x7, 0x10, op_code);
  2825. rtl931x_write_sds_phy(asds, 0x6, 0x1d, 0x0480);
  2826. rtl931x_write_sds_phy(asds, 0x6, 0xe, 0x0400);
  2827. }
  2828. break;
  2829. case PHY_INTERFACE_MODE_10GBASER: /* MII_10GR / MII_10GR1000BX_AUTO: */
  2830. /* configure 10GR fiber mode=1 */
  2831. rtl9310_sds_field_w(asds, 0x1f, 0xb, 1, 1, 1);
  2832. /* init fiber_1g */
  2833. rtl9310_sds_field_w(dSds, 0x3, 0x13, 15, 14, 0);
  2834. rtl9310_sds_field_w(dSds, 0x2, 0x0, 12, 12, 1);
  2835. rtl9310_sds_field_w(dSds, 0x2, 0x0, 6, 6, 1);
  2836. rtl9310_sds_field_w(dSds, 0x2, 0x0, 13, 13, 0);
  2837. /* init auto */
  2838. rtl9310_sds_field_w(asds, 0x1f, 13, 15, 0, 0x109e);
  2839. rtl9310_sds_field_w(asds, 0x1f, 0x6, 14, 10, 0x8);
  2840. rtl9310_sds_field_w(asds, 0x1f, 0x7, 10, 4, 0x7f);
  2841. break;
  2842. case PHY_INTERFACE_MODE_HSGMII:
  2843. rtl9310_sds_field_w(dSds, 0x1, 0x14, 8, 8, 1);
  2844. break;
  2845. case PHY_INTERFACE_MODE_1000BASEX: /* MII_1000BX_FIBER */
  2846. rtl9310_sds_field_w(dSds, 0x3, 0x13, 15, 14, 0);
  2847. rtl9310_sds_field_w(dSds, 0x2, 0x0, 12, 12, 1);
  2848. rtl9310_sds_field_w(dSds, 0x2, 0x0, 6, 6, 1);
  2849. rtl9310_sds_field_w(dSds, 0x2, 0x0, 13, 13, 0);
  2850. break;
  2851. case PHY_INTERFACE_MODE_SGMII:
  2852. rtl9310_sds_field_w(asds, 0x24, 0x9, 15, 15, 0);
  2853. break;
  2854. case PHY_INTERFACE_MODE_2500BASEX:
  2855. rtl9310_sds_field_w(dSds, 0x1, 0x14, 8, 8, 1);
  2856. break;
  2857. case PHY_INTERFACE_MODE_QSGMII:
  2858. default:
  2859. pr_info("%s: PHY mode %s not supported by SerDes %d\n",
  2860. __func__, phy_modes(mode), sds);
  2861. return;
  2862. }
  2863. rtl931x_cmu_type_set(asds, mode, chiptype);
  2864. if (sds >= 2 && sds <= 13) {
  2865. if (chiptype)
  2866. rtl931x_write_sds_phy(asds, 0x2E, 0x1, board_sds_tx_type1[sds - 2]);
  2867. else {
  2868. val = 0xa0000;
  2869. sw_w32(val, RTL931X_CHIP_INFO_ADDR);
  2870. val = sw_r32(RTL931X_CHIP_INFO_ADDR);
  2871. if (val & BIT(28)) /* consider 9311 etc. RTL9313_CHIP_ID == HWP_CHIP_ID(unit)) */
  2872. {
  2873. rtl931x_write_sds_phy(asds, 0x2E, 0x1, board_sds_tx2[sds - 2]);
  2874. } else {
  2875. rtl931x_write_sds_phy(asds, 0x2E, 0x1, board_sds_tx[sds - 2]);
  2876. }
  2877. val = 0;
  2878. sw_w32(val, RTL931X_CHIP_INFO_ADDR);
  2879. }
  2880. }
  2881. val = ori & ~BIT(sds);
  2882. sw_w32(val, RTL931X_PS_SERDES_OFF_MODE_CTRL_ADDR);
  2883. pr_debug("%s: RTL931X_PS_SERDES_OFF_MODE_CTRL_ADDR 0x%08X\n", __func__, sw_r32(RTL931X_PS_SERDES_OFF_MODE_CTRL_ADDR));
  2884. if (mode == PHY_INTERFACE_MODE_XGMII ||
  2885. mode == PHY_INTERFACE_MODE_QSGMII ||
  2886. mode == PHY_INTERFACE_MODE_HSGMII ||
  2887. mode == PHY_INTERFACE_MODE_SGMII ||
  2888. mode == PHY_INTERFACE_MODE_USXGMII) {
  2889. if (mode == PHY_INTERFACE_MODE_XGMII)
  2890. rtl931x_sds_mii_mode_set(sds, mode);
  2891. else
  2892. rtl931x_sds_fiber_mode_set(sds, mode);
  2893. }
  2894. }
  2895. int rtl931x_sds_cmu_band_set(int sds, bool enable, u32 band, phy_interface_t mode)
  2896. {
  2897. u32 asds;
  2898. int page = rtl931x_sds_cmu_page_get(mode);
  2899. sds -= (sds % 2);
  2900. sds = sds & ~1;
  2901. asds = rtl931x_get_analog_sds(sds);
  2902. page += 1;
  2903. if (enable) {
  2904. rtl9310_sds_field_w(asds, page, 0x7, 13, 13, 0);
  2905. rtl9310_sds_field_w(asds, page, 0x7, 11, 11, 0);
  2906. } else {
  2907. rtl9310_sds_field_w(asds, page, 0x7, 13, 13, 0);
  2908. rtl9310_sds_field_w(asds, page, 0x7, 11, 11, 0);
  2909. }
  2910. rtl9310_sds_field_w(asds, page, 0x7, 4, 0, band);
  2911. rtl931x_sds_rst(sds);
  2912. return 0;
  2913. }
  2914. int rtl931x_sds_cmu_band_get(int sds, phy_interface_t mode)
  2915. {
  2916. int page = rtl931x_sds_cmu_page_get(mode);
  2917. u32 asds, band;
  2918. sds -= (sds % 2);
  2919. asds = rtl931x_get_analog_sds(sds);
  2920. page += 1;
  2921. rtl931x_write_sds_phy(asds, 0x1f, 0x02, 73);
  2922. rtl9310_sds_field_w(asds, page, 0x5, 15, 15, 1);
  2923. band = rtl9310_sds_field_r(asds, 0x1f, 0x15, 8, 3);
  2924. pr_info("%s band is: %d\n", __func__, band);
  2925. return band;
  2926. }
  2927. int rtl931x_link_sts_get(u32 sds)
  2928. {
  2929. u32 sts, sts1, latch_sts, latch_sts1;
  2930. if (0){
  2931. u32 xsg_sdsid_0, xsg_sdsid_1;
  2932. xsg_sdsid_0 = sds < 2 ? sds : (sds - 1) * 2;
  2933. xsg_sdsid_1 = xsg_sdsid_0 + 1;
  2934. sts = rtl9310_sds_field_r(xsg_sdsid_0, 0x1, 29, 8, 0);
  2935. sts1 = rtl9310_sds_field_r(xsg_sdsid_1, 0x1, 29, 8, 0);
  2936. latch_sts = rtl9310_sds_field_r(xsg_sdsid_0, 0x1, 30, 8, 0);
  2937. latch_sts1 = rtl9310_sds_field_r(xsg_sdsid_1, 0x1, 30, 8, 0);
  2938. } else {
  2939. u32 asds, dsds;
  2940. asds = rtl931x_get_analog_sds(sds);
  2941. sts = rtl9310_sds_field_r(asds, 0x5, 0, 12, 12);
  2942. latch_sts = rtl9310_sds_field_r(asds, 0x4, 1, 2, 2);
  2943. dsds = sds < 2 ? sds : (sds - 1) * 2;
  2944. latch_sts1 = rtl9310_sds_field_r(dsds, 0x2, 1, 2, 2);
  2945. sts1 = rtl9310_sds_field_r(dsds, 0x2, 1, 2, 2);
  2946. }
  2947. pr_info("%s: serdes %d sts %d, sts1 %d, latch_sts %d, latch_sts1 %d\n", __func__,
  2948. sds, sts, sts1, latch_sts, latch_sts1);
  2949. return sts1;
  2950. }
  2951. static int rtl8214fc_sfp_insert(void *upstream, const struct sfp_eeprom_id *id)
  2952. {
  2953. struct phy_device *phydev = upstream;
  2954. rtl8214fc_media_set(phydev, true);
  2955. return 0;
  2956. }
  2957. static void rtl8214fc_sfp_remove(void *upstream)
  2958. {
  2959. struct phy_device *phydev = upstream;
  2960. rtl8214fc_media_set(phydev, false);
  2961. }
  2962. static const struct sfp_upstream_ops rtl8214fc_sfp_ops = {
  2963. .attach = phy_sfp_attach,
  2964. .detach = phy_sfp_detach,
  2965. .module_insert = rtl8214fc_sfp_insert,
  2966. .module_remove = rtl8214fc_sfp_remove,
  2967. };
  2968. static int rtl8214fc_phy_probe(struct phy_device *phydev)
  2969. {
  2970. struct device *dev = &phydev->mdio.dev;
  2971. int addr = phydev->mdio.addr;
  2972. int ret = 0;
  2973. /* 839x has internal SerDes */
  2974. if (soc_info.id == 0x8393)
  2975. return -ENODEV;
  2976. /* All base addresses of the PHYs start at multiples of 8 */
  2977. devm_phy_package_join(dev, phydev, addr & (~7),
  2978. sizeof(struct rtl83xx_shared_private));
  2979. if (!(addr % 8)) {
  2980. struct rtl83xx_shared_private *shared = phydev->shared->priv;
  2981. shared->name = "RTL8214FC";
  2982. /* Configuration must be done while patching still possible */
  2983. ret = rtl8380_configure_rtl8214fc(phydev);
  2984. if (ret)
  2985. return ret;
  2986. }
  2987. return phy_sfp_probe(phydev, &rtl8214fc_sfp_ops);
  2988. }
  2989. static int rtl8214c_phy_probe(struct phy_device *phydev)
  2990. {
  2991. struct device *dev = &phydev->mdio.dev;
  2992. int addr = phydev->mdio.addr;
  2993. /* All base addresses of the PHYs start at multiples of 8 */
  2994. devm_phy_package_join(dev, phydev, addr & (~7),
  2995. sizeof(struct rtl83xx_shared_private));
  2996. if (!(addr % 8)) {
  2997. struct rtl83xx_shared_private *shared = phydev->shared->priv;
  2998. shared->name = "RTL8214C";
  2999. /* Configuration must be done whil patching still possible */
  3000. return rtl8380_configure_rtl8214c(phydev);
  3001. }
  3002. return 0;
  3003. }
  3004. static int rtl8218b_ext_phy_probe(struct phy_device *phydev)
  3005. {
  3006. struct device *dev = &phydev->mdio.dev;
  3007. int addr = phydev->mdio.addr;
  3008. /* All base addresses of the PHYs start at multiples of 8 */
  3009. devm_phy_package_join(dev, phydev, addr & (~7),
  3010. sizeof(struct rtl83xx_shared_private));
  3011. if (!(addr % 8)) {
  3012. struct rtl83xx_shared_private *shared = phydev->shared->priv;
  3013. shared->name = "RTL8218B (external)";
  3014. if (soc_info.family == RTL8380_FAMILY_ID) {
  3015. /* Configuration must be done while patching still possible */
  3016. return rtl8380_configure_ext_rtl8218b(phydev);
  3017. }
  3018. }
  3019. return 0;
  3020. }
  3021. static int rtl8218b_int_phy_probe(struct phy_device *phydev)
  3022. {
  3023. struct device *dev = &phydev->mdio.dev;
  3024. int addr = phydev->mdio.addr;
  3025. if (soc_info.family != RTL8380_FAMILY_ID)
  3026. return -ENODEV;
  3027. if (addr >= 24)
  3028. return -ENODEV;
  3029. pr_debug("%s: id: %d\n", __func__, addr);
  3030. /* All base addresses of the PHYs start at multiples of 8 */
  3031. devm_phy_package_join(dev, phydev, addr & (~7),
  3032. sizeof(struct rtl83xx_shared_private));
  3033. if (!(addr % 8)) {
  3034. struct rtl83xx_shared_private *shared = phydev->shared->priv;
  3035. shared->name = "RTL8218B (internal)";
  3036. /* Configuration must be done while patching still possible */
  3037. return rtl8380_configure_int_rtl8218b(phydev);
  3038. }
  3039. return 0;
  3040. }
  3041. static int rtl8218d_phy_probe(struct phy_device *phydev)
  3042. {
  3043. struct device *dev = &phydev->mdio.dev;
  3044. int addr = phydev->mdio.addr;
  3045. pr_debug("%s: id: %d\n", __func__, addr);
  3046. /* All base addresses of the PHYs start at multiples of 8 */
  3047. devm_phy_package_join(dev, phydev, addr & (~7),
  3048. sizeof(struct rtl83xx_shared_private));
  3049. /* All base addresses of the PHYs start at multiples of 8 */
  3050. if (!(addr % 8)) {
  3051. struct rtl83xx_shared_private *shared = phydev->shared->priv;
  3052. shared->name = "RTL8218D";
  3053. /* Configuration must be done while patching still possible */
  3054. /* TODO: return configure_rtl8218d(phydev); */
  3055. }
  3056. return 0;
  3057. }
  3058. static int rtl838x_serdes_probe(struct phy_device *phydev)
  3059. {
  3060. int addr = phydev->mdio.addr;
  3061. if (soc_info.family != RTL8380_FAMILY_ID)
  3062. return -ENODEV;
  3063. if (addr < 24)
  3064. return -ENODEV;
  3065. /* On the RTL8380M, PHYs 24-27 connect to the internal SerDes */
  3066. if (soc_info.id == 0x8380) {
  3067. if (addr == 24)
  3068. return rtl8380_configure_serdes(phydev);
  3069. return 0;
  3070. }
  3071. return -ENODEV;
  3072. }
  3073. static int rtl8393_serdes_probe(struct phy_device *phydev)
  3074. {
  3075. int addr = phydev->mdio.addr;
  3076. pr_info("%s: id: %d\n", __func__, addr);
  3077. if (soc_info.family != RTL8390_FAMILY_ID)
  3078. return -ENODEV;
  3079. if (addr < 24)
  3080. return -ENODEV;
  3081. return rtl8390_configure_serdes(phydev);
  3082. }
  3083. static int rtl8390_serdes_probe(struct phy_device *phydev)
  3084. {
  3085. int addr = phydev->mdio.addr;
  3086. if (soc_info.family != RTL8390_FAMILY_ID)
  3087. return -ENODEV;
  3088. if (addr < 24)
  3089. return -ENODEV;
  3090. return rtl8390_configure_generic(phydev);
  3091. }
  3092. static int rtl9300_serdes_probe(struct phy_device *phydev)
  3093. {
  3094. if (soc_info.family != RTL9300_FAMILY_ID)
  3095. return -ENODEV;
  3096. phydev_info(phydev, "Detected internal RTL9300 Serdes\n");
  3097. return 0;
  3098. }
  3099. static struct phy_driver rtl83xx_phy_driver[] = {
  3100. {
  3101. PHY_ID_MATCH_MODEL(PHY_ID_RTL8214C),
  3102. .name = "Realtek RTL8214C",
  3103. .features = PHY_GBIT_FEATURES,
  3104. .flags = PHY_HAS_REALTEK_PAGES,
  3105. .match_phy_device = rtl8214c_match_phy_device,
  3106. .probe = rtl8214c_phy_probe,
  3107. .suspend = genphy_suspend,
  3108. .resume = genphy_resume,
  3109. .set_loopback = genphy_loopback,
  3110. },
  3111. {
  3112. PHY_ID_MATCH_MODEL(PHY_ID_RTL8214FC),
  3113. .name = "Realtek RTL8214FC",
  3114. .features = PHY_GBIT_FIBRE_FEATURES,
  3115. .flags = PHY_HAS_REALTEK_PAGES,
  3116. .match_phy_device = rtl8214fc_match_phy_device,
  3117. .probe = rtl8214fc_phy_probe,
  3118. .suspend = rtl8214fc_suspend,
  3119. .resume = rtl8214fc_resume,
  3120. .set_loopback = genphy_loopback,
  3121. .set_port = rtl8214fc_set_port,
  3122. .get_port = rtl8214fc_get_port,
  3123. .set_eee = rtl8214fc_set_eee,
  3124. .get_eee = rtl8214fc_get_eee,
  3125. },
  3126. {
  3127. PHY_ID_MATCH_MODEL(PHY_ID_RTL8218B_E),
  3128. .name = "Realtek RTL8218B (external)",
  3129. .features = PHY_GBIT_FEATURES,
  3130. .flags = PHY_HAS_REALTEK_PAGES,
  3131. .match_phy_device = rtl8218b_ext_match_phy_device,
  3132. .probe = rtl8218b_ext_phy_probe,
  3133. .suspend = genphy_suspend,
  3134. .resume = genphy_resume,
  3135. .set_loopback = genphy_loopback,
  3136. .set_eee = rtl8218b_set_eee,
  3137. .get_eee = rtl8218b_get_eee,
  3138. },
  3139. {
  3140. PHY_ID_MATCH_MODEL(PHY_ID_RTL8218D),
  3141. .name = "REALTEK RTL8218D",
  3142. .features = PHY_GBIT_FEATURES,
  3143. .flags = PHY_HAS_REALTEK_PAGES,
  3144. .probe = rtl8218d_phy_probe,
  3145. .suspend = genphy_suspend,
  3146. .resume = genphy_resume,
  3147. .set_loopback = genphy_loopback,
  3148. .set_eee = rtl8218d_set_eee,
  3149. .get_eee = rtl8218d_get_eee,
  3150. },
  3151. {
  3152. PHY_ID_MATCH_MODEL(PHY_ID_RTL8221B),
  3153. .name = "REALTEK RTL8221B",
  3154. .features = PHY_GBIT_FEATURES,
  3155. .flags = PHY_HAS_REALTEK_PAGES,
  3156. .suspend = genphy_suspend,
  3157. .resume = genphy_resume,
  3158. .set_loopback = genphy_loopback,
  3159. .read_page = rtl8226_read_page,
  3160. .write_page = rtl8226_write_page,
  3161. .read_status = rtl8226_read_status,
  3162. .config_aneg = rtl8226_config_aneg,
  3163. .set_eee = rtl8226_set_eee,
  3164. .get_eee = rtl8226_get_eee,
  3165. },
  3166. {
  3167. PHY_ID_MATCH_MODEL(PHY_ID_RTL8226),
  3168. .name = "REALTEK RTL8226",
  3169. .features = PHY_GBIT_FEATURES,
  3170. .flags = PHY_HAS_REALTEK_PAGES,
  3171. .suspend = genphy_suspend,
  3172. .resume = genphy_resume,
  3173. .set_loopback = genphy_loopback,
  3174. .read_page = rtl8226_read_page,
  3175. .write_page = rtl8226_write_page,
  3176. .read_status = rtl8226_read_status,
  3177. .config_aneg = rtl8226_config_aneg,
  3178. .set_eee = rtl8226_set_eee,
  3179. .get_eee = rtl8226_get_eee,
  3180. },
  3181. {
  3182. PHY_ID_MATCH_MODEL(PHY_ID_RTL8218B_I),
  3183. .name = "Realtek RTL8218B (internal)",
  3184. .features = PHY_GBIT_FEATURES,
  3185. .flags = PHY_HAS_REALTEK_PAGES,
  3186. .probe = rtl8218b_int_phy_probe,
  3187. .suspend = genphy_suspend,
  3188. .resume = genphy_resume,
  3189. .set_loopback = genphy_loopback,
  3190. .set_eee = rtl8218b_set_eee,
  3191. .get_eee = rtl8218b_get_eee,
  3192. },
  3193. {
  3194. PHY_ID_MATCH_MODEL(PHY_ID_RTL8218B_I),
  3195. .name = "Realtek RTL8380 SERDES",
  3196. .features = PHY_GBIT_FIBRE_FEATURES,
  3197. .flags = PHY_HAS_REALTEK_PAGES,
  3198. .probe = rtl838x_serdes_probe,
  3199. .suspend = genphy_suspend,
  3200. .resume = genphy_resume,
  3201. .set_loopback = genphy_loopback,
  3202. .read_status = rtl8380_read_status,
  3203. },
  3204. {
  3205. PHY_ID_MATCH_MODEL(PHY_ID_RTL8393_I),
  3206. .name = "Realtek RTL8393 SERDES",
  3207. .features = PHY_GBIT_FIBRE_FEATURES,
  3208. .flags = PHY_HAS_REALTEK_PAGES,
  3209. .probe = rtl8393_serdes_probe,
  3210. .suspend = genphy_suspend,
  3211. .resume = genphy_resume,
  3212. .set_loopback = genphy_loopback,
  3213. .read_status = rtl8393_read_status,
  3214. },
  3215. {
  3216. PHY_ID_MATCH_MODEL(PHY_ID_RTL8390_GENERIC),
  3217. .name = "Realtek RTL8390 Generic",
  3218. .features = PHY_GBIT_FIBRE_FEATURES,
  3219. .flags = PHY_HAS_REALTEK_PAGES,
  3220. .probe = rtl8390_serdes_probe,
  3221. .suspend = genphy_suspend,
  3222. .resume = genphy_resume,
  3223. .set_loopback = genphy_loopback,
  3224. },
  3225. {
  3226. PHY_ID_MATCH_MODEL(PHY_ID_RTL9300_I),
  3227. .name = "REALTEK RTL9300 SERDES",
  3228. .features = PHY_GBIT_FIBRE_FEATURES,
  3229. .flags = PHY_HAS_REALTEK_PAGES,
  3230. .probe = rtl9300_serdes_probe,
  3231. .suspend = genphy_suspend,
  3232. .resume = genphy_resume,
  3233. .set_loopback = genphy_loopback,
  3234. .read_status = rtl9300_read_status,
  3235. },
  3236. };
  3237. module_phy_driver(rtl83xx_phy_driver);
  3238. static struct mdio_device_id __maybe_unused rtl83xx_tbl[] = {
  3239. { PHY_ID_MATCH_MODEL(PHY_ID_RTL8214FC) },
  3240. { }
  3241. };
  3242. MODULE_DEVICE_TABLE(mdio, rtl83xx_tbl);
  3243. MODULE_AUTHOR("B. Koblitz");
  3244. MODULE_DESCRIPTION("RTL83xx PHY driver");
  3245. MODULE_LICENSE("GPL");