FlashPoint.c 193 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341234223432344234523462347234823492350235123522353235423552356235723582359236023612362236323642365236623672368236923702371237223732374237523762377237823792380238123822383238423852386238723882389239023912392239323942395239623972398239924002401240224032404240524062407240824092410241124122413241424152416241724182419242024212422242324242425242624272428242924302431243224332434243524362437243824392440244124422443244424452446244724482449245024512452245324542455245624572458245924602461246224632464246524662467246824692470247124722473247424752476247724782479248024812482248324842485248624872488248924902491249224932494249524962497249824992500250125022503250425052506250725082509251025112512251325142515251625172518251925202521252225232524252525262527252825292530253125322533253425352536253725382539254025412542254325442545254625472548254925502551255225532554255525562557255825592560256125622563256425652566256725682569257025712572257325742575257625772578257925802581258225832584258525862587258825892590259125922593259425952596259725982599260026012602260326042605260626072608260926102611261226132614261526162617261826192620262126222623262426252626262726282629263026312632263326342635263626372638263926402641264226432644264526462647264826492650265126522653265426552656265726582659266026612662266326642665266626672668266926702671267226732674267526762677267826792680268126822683268426852686268726882689269026912692269326942695269626972698269927002701270227032704270527062707270827092710271127122713271427152716271727182719272027212722272327242725272627272728272927302731273227332734273527362737273827392740274127422743274427452746274727482749275027512752275327542755275627572758275927602761276227632764276527662767276827692770277127722773277427752776277727782779278027812782278327842785278627872788278927902791279227932794279527962797279827992800280128022803280428052806280728082809281028112812281328142815281628172818281928202821282228232824282528262827282828292830283128322833283428352836283728382839284028412842284328442845284628472848284928502851285228532854285528562857285828592860286128622863286428652866286728682869287028712872287328742875287628772878287928802881288228832884288528862887288828892890289128922893289428952896289728982899290029012902290329042905290629072908290929102911291229132914291529162917291829192920292129222923292429252926292729282929293029312932293329342935293629372938293929402941294229432944294529462947294829492950295129522953295429552956295729582959296029612962296329642965296629672968296929702971297229732974297529762977297829792980298129822983298429852986298729882989299029912992299329942995299629972998299930003001300230033004300530063007300830093010301130123013301430153016301730183019302030213022302330243025302630273028302930303031303230333034303530363037303830393040304130423043304430453046304730483049305030513052305330543055305630573058305930603061306230633064306530663067306830693070307130723073307430753076307730783079308030813082308330843085308630873088308930903091309230933094309530963097309830993100310131023103310431053106310731083109311031113112311331143115311631173118311931203121312231233124312531263127312831293130313131323133313431353136313731383139314031413142314331443145314631473148314931503151315231533154315531563157315831593160316131623163316431653166316731683169317031713172317331743175317631773178317931803181318231833184318531863187318831893190319131923193319431953196319731983199320032013202320332043205320632073208320932103211321232133214321532163217321832193220322132223223322432253226322732283229323032313232323332343235323632373238323932403241324232433244324532463247324832493250325132523253325432553256325732583259326032613262326332643265326632673268326932703271327232733274327532763277327832793280328132823283328432853286328732883289329032913292329332943295329632973298329933003301330233033304330533063307330833093310331133123313331433153316331733183319332033213322332333243325332633273328332933303331333233333334333533363337333833393340334133423343334433453346334733483349335033513352335333543355335633573358335933603361336233633364336533663367336833693370337133723373337433753376337733783379338033813382338333843385338633873388338933903391339233933394339533963397339833993400340134023403340434053406340734083409341034113412341334143415341634173418341934203421342234233424342534263427342834293430343134323433343434353436343734383439344034413442344334443445344634473448344934503451345234533454345534563457345834593460346134623463346434653466346734683469347034713472347334743475347634773478347934803481348234833484348534863487348834893490349134923493349434953496349734983499350035013502350335043505350635073508350935103511351235133514351535163517351835193520352135223523352435253526352735283529353035313532353335343535353635373538353935403541354235433544354535463547354835493550355135523553355435553556355735583559356035613562356335643565356635673568356935703571357235733574357535763577357835793580358135823583358435853586358735883589359035913592359335943595359635973598359936003601360236033604360536063607360836093610361136123613361436153616361736183619362036213622362336243625362636273628362936303631363236333634363536363637363836393640364136423643364436453646364736483649365036513652365336543655365636573658365936603661366236633664366536663667366836693670367136723673367436753676367736783679368036813682368336843685368636873688368936903691369236933694369536963697369836993700370137023703370437053706370737083709371037113712371337143715371637173718371937203721372237233724372537263727372837293730373137323733373437353736373737383739374037413742374337443745374637473748374937503751375237533754375537563757375837593760376137623763376437653766376737683769377037713772377337743775377637773778377937803781378237833784378537863787378837893790379137923793379437953796379737983799380038013802380338043805380638073808380938103811381238133814381538163817381838193820382138223823382438253826382738283829383038313832383338343835383638373838383938403841384238433844384538463847384838493850385138523853385438553856385738583859386038613862386338643865386638673868386938703871387238733874387538763877387838793880388138823883388438853886388738883889389038913892389338943895389638973898389939003901390239033904390539063907390839093910391139123913391439153916391739183919392039213922392339243925392639273928392939303931393239333934393539363937393839393940394139423943394439453946394739483949395039513952395339543955395639573958395939603961396239633964396539663967396839693970397139723973397439753976397739783979398039813982398339843985398639873988398939903991399239933994399539963997399839994000400140024003400440054006400740084009401040114012401340144015401640174018401940204021402240234024402540264027402840294030403140324033403440354036403740384039404040414042404340444045404640474048404940504051405240534054405540564057405840594060406140624063406440654066406740684069407040714072407340744075407640774078407940804081408240834084408540864087408840894090409140924093409440954096409740984099410041014102410341044105410641074108410941104111411241134114411541164117411841194120412141224123412441254126412741284129413041314132413341344135413641374138413941404141414241434144414541464147414841494150415141524153415441554156415741584159416041614162416341644165416641674168416941704171417241734174417541764177417841794180418141824183418441854186418741884189419041914192419341944195419641974198419942004201420242034204420542064207420842094210421142124213421442154216421742184219422042214222422342244225422642274228422942304231423242334234423542364237423842394240424142424243424442454246424742484249425042514252425342544255425642574258425942604261426242634264426542664267426842694270427142724273427442754276427742784279428042814282428342844285428642874288428942904291429242934294429542964297429842994300430143024303430443054306430743084309431043114312431343144315431643174318431943204321432243234324432543264327432843294330433143324333433443354336433743384339434043414342434343444345434643474348434943504351435243534354435543564357435843594360436143624363436443654366436743684369437043714372437343744375437643774378437943804381438243834384438543864387438843894390439143924393439443954396439743984399440044014402440344044405440644074408440944104411441244134414441544164417441844194420442144224423442444254426442744284429443044314432443344344435443644374438443944404441444244434444444544464447444844494450445144524453445444554456445744584459446044614462446344644465446644674468446944704471447244734474447544764477447844794480448144824483448444854486448744884489449044914492449344944495449644974498449945004501450245034504450545064507450845094510451145124513451445154516451745184519452045214522452345244525452645274528452945304531453245334534453545364537453845394540454145424543454445454546454745484549455045514552455345544555455645574558455945604561456245634564456545664567456845694570457145724573457445754576457745784579458045814582458345844585458645874588458945904591459245934594459545964597459845994600460146024603460446054606460746084609461046114612461346144615461646174618461946204621462246234624462546264627462846294630463146324633463446354636463746384639464046414642464346444645464646474648464946504651465246534654465546564657465846594660466146624663466446654666466746684669467046714672467346744675467646774678467946804681468246834684468546864687468846894690469146924693469446954696469746984699470047014702470347044705470647074708470947104711471247134714471547164717471847194720472147224723472447254726472747284729473047314732473347344735473647374738473947404741474247434744474547464747474847494750475147524753475447554756475747584759476047614762476347644765476647674768476947704771477247734774477547764777477847794780478147824783478447854786478747884789479047914792479347944795479647974798479948004801480248034804480548064807480848094810481148124813481448154816481748184819482048214822482348244825482648274828482948304831483248334834483548364837483848394840484148424843484448454846484748484849485048514852485348544855485648574858485948604861486248634864486548664867486848694870487148724873487448754876487748784879488048814882488348844885488648874888488948904891489248934894489548964897489848994900490149024903490449054906490749084909491049114912491349144915491649174918491949204921492249234924492549264927492849294930493149324933493449354936493749384939494049414942494349444945494649474948494949504951495249534954495549564957495849594960496149624963496449654966496749684969497049714972497349744975497649774978497949804981498249834984498549864987498849894990499149924993499449954996499749984999500050015002500350045005500650075008500950105011501250135014501550165017501850195020502150225023502450255026502750285029503050315032503350345035503650375038503950405041504250435044504550465047504850495050505150525053505450555056505750585059506050615062506350645065506650675068506950705071507250735074507550765077507850795080508150825083508450855086508750885089509050915092509350945095509650975098509951005101510251035104510551065107510851095110511151125113511451155116511751185119512051215122512351245125512651275128512951305131513251335134513551365137513851395140514151425143514451455146514751485149515051515152515351545155515651575158515951605161516251635164516551665167516851695170517151725173517451755176517751785179518051815182518351845185518651875188518951905191519251935194519551965197519851995200520152025203520452055206520752085209521052115212521352145215521652175218521952205221522252235224522552265227522852295230523152325233523452355236523752385239524052415242524352445245524652475248524952505251525252535254525552565257525852595260526152625263526452655266526752685269527052715272527352745275527652775278527952805281528252835284528552865287528852895290529152925293529452955296529752985299530053015302530353045305530653075308530953105311531253135314531553165317531853195320532153225323532453255326532753285329533053315332533353345335533653375338533953405341534253435344534553465347534853495350535153525353535453555356535753585359536053615362536353645365536653675368536953705371537253735374537553765377537853795380538153825383538453855386538753885389539053915392539353945395539653975398539954005401540254035404540554065407540854095410541154125413541454155416541754185419542054215422542354245425542654275428542954305431543254335434543554365437543854395440544154425443544454455446544754485449545054515452545354545455545654575458545954605461546254635464546554665467546854695470547154725473547454755476547754785479548054815482548354845485548654875488548954905491549254935494549554965497549854995500550155025503550455055506550755085509551055115512551355145515551655175518551955205521552255235524552555265527552855295530553155325533553455355536553755385539554055415542554355445545554655475548554955505551555255535554555555565557555855595560556155625563556455655566556755685569557055715572557355745575557655775578557955805581558255835584558555865587558855895590559155925593559455955596559755985599560056015602560356045605560656075608560956105611561256135614561556165617561856195620562156225623562456255626562756285629563056315632563356345635563656375638563956405641564256435644564556465647564856495650565156525653565456555656565756585659566056615662566356645665566656675668566956705671567256735674567556765677567856795680568156825683568456855686568756885689569056915692569356945695569656975698569957005701570257035704570557065707570857095710571157125713571457155716571757185719572057215722572357245725572657275728572957305731573257335734573557365737573857395740574157425743574457455746574757485749575057515752575357545755575657575758575957605761576257635764576557665767576857695770577157725773577457755776577757785779578057815782578357845785578657875788578957905791579257935794579557965797579857995800580158025803580458055806580758085809581058115812581358145815581658175818581958205821582258235824582558265827582858295830583158325833583458355836583758385839584058415842584358445845584658475848584958505851585258535854585558565857585858595860586158625863586458655866586758685869587058715872587358745875587658775878587958805881588258835884588558865887588858895890589158925893589458955896589758985899590059015902590359045905590659075908590959105911591259135914591559165917591859195920592159225923592459255926592759285929593059315932593359345935593659375938593959405941594259435944594559465947594859495950595159525953595459555956595759585959596059615962596359645965596659675968596959705971597259735974597559765977597859795980598159825983598459855986598759885989599059915992599359945995599659975998599960006001600260036004600560066007600860096010601160126013601460156016601760186019602060216022602360246025602660276028602960306031603260336034603560366037603860396040604160426043604460456046604760486049605060516052605360546055605660576058605960606061606260636064606560666067606860696070607160726073607460756076607760786079608060816082608360846085608660876088608960906091609260936094609560966097609860996100610161026103610461056106610761086109611061116112611361146115611661176118611961206121612261236124612561266127612861296130613161326133613461356136613761386139614061416142614361446145614661476148614961506151615261536154615561566157615861596160616161626163616461656166616761686169617061716172617361746175617661776178617961806181618261836184618561866187618861896190619161926193619461956196619761986199620062016202620362046205620662076208620962106211621262136214621562166217621862196220622162226223622462256226622762286229623062316232623362346235623662376238623962406241624262436244624562466247624862496250625162526253625462556256625762586259626062616262626362646265626662676268626962706271627262736274627562766277627862796280628162826283628462856286628762886289629062916292629362946295629662976298629963006301630263036304630563066307630863096310631163126313631463156316631763186319632063216322632363246325632663276328632963306331633263336334633563366337633863396340634163426343634463456346634763486349635063516352635363546355635663576358635963606361636263636364636563666367636863696370637163726373637463756376637763786379638063816382638363846385638663876388638963906391639263936394639563966397639863996400640164026403640464056406640764086409641064116412641364146415641664176418641964206421642264236424642564266427642864296430643164326433643464356436643764386439644064416442644364446445644664476448644964506451645264536454645564566457645864596460646164626463646464656466646764686469647064716472647364746475647664776478647964806481648264836484648564866487648864896490649164926493649464956496649764986499650065016502650365046505650665076508650965106511651265136514651565166517651865196520652165226523652465256526652765286529653065316532653365346535653665376538653965406541654265436544654565466547654865496550655165526553655465556556655765586559656065616562656365646565656665676568656965706571657265736574657565766577657865796580658165826583658465856586658765886589659065916592659365946595659665976598659966006601660266036604660566066607660866096610661166126613661466156616661766186619662066216622662366246625662666276628662966306631663266336634663566366637663866396640664166426643664466456646664766486649665066516652665366546655665666576658665966606661666266636664666566666667666866696670667166726673667466756676667766786679668066816682668366846685668666876688668966906691669266936694669566966697669866996700670167026703670467056706670767086709671067116712671367146715671667176718671967206721672267236724672567266727672867296730673167326733673467356736673767386739674067416742674367446745674667476748674967506751675267536754675567566757675867596760676167626763676467656766676767686769677067716772677367746775677667776778677967806781678267836784678567866787678867896790679167926793679467956796679767986799680068016802680368046805680668076808680968106811681268136814681568166817681868196820682168226823682468256826682768286829683068316832683368346835683668376838683968406841684268436844684568466847684868496850685168526853685468556856685768586859686068616862686368646865686668676868686968706871687268736874687568766877687868796880688168826883688468856886688768886889689068916892689368946895689668976898689969006901690269036904690569066907690869096910691169126913691469156916691769186919692069216922692369246925692669276928692969306931693269336934693569366937693869396940694169426943694469456946694769486949695069516952695369546955695669576958695969606961696269636964696569666967696869696970697169726973697469756976697769786979698069816982698369846985698669876988698969906991699269936994699569966997699869997000700170027003700470057006700770087009701070117012701370147015701670177018701970207021702270237024702570267027702870297030703170327033703470357036703770387039704070417042704370447045704670477048704970507051705270537054705570567057705870597060706170627063706470657066706770687069707070717072707370747075707670777078707970807081708270837084708570867087708870897090709170927093709470957096709770987099710071017102710371047105710671077108710971107111711271137114711571167117711871197120712171227123712471257126712771287129713071317132713371347135713671377138713971407141714271437144714571467147714871497150715171527153715471557156715771587159716071617162716371647165716671677168716971707171717271737174717571767177717871797180718171827183718471857186718771887189719071917192719371947195719671977198719972007201720272037204720572067207720872097210721172127213721472157216721772187219722072217222722372247225722672277228722972307231723272337234723572367237723872397240724172427243724472457246724772487249725072517252725372547255725672577258725972607261726272637264726572667267726872697270727172727273727472757276727772787279728072817282728372847285728672877288728972907291729272937294729572967297729872997300730173027303730473057306730773087309731073117312731373147315731673177318731973207321732273237324732573267327732873297330733173327333733473357336733773387339734073417342734373447345734673477348734973507351735273537354735573567357735873597360736173627363736473657366736773687369737073717372737373747375737673777378737973807381738273837384738573867387738873897390739173927393739473957396739773987399740074017402740374047405740674077408740974107411741274137414741574167417741874197420742174227423742474257426742774287429743074317432743374347435743674377438743974407441744274437444744574467447744874497450745174527453745474557456745774587459746074617462746374647465746674677468746974707471747274737474747574767477747874797480748174827483748474857486748774887489749074917492749374947495749674977498749975007501750275037504750575067507750875097510751175127513751475157516751775187519752075217522752375247525752675277528752975307531753275337534753575367537753875397540754175427543754475457546754775487549755075517552755375547555755675577558755975607561756275637564756575667567756875697570757175727573757475757576757775787579758075817582758375847585758675877588
  1. /*
  2. FlashPoint.c -- FlashPoint SCCB Manager for Linux
  3. This file contains the FlashPoint SCCB Manager from BusLogic's FlashPoint
  4. Driver Developer's Kit, with minor modifications by Leonard N. Zubkoff for
  5. Linux compatibility. It was provided by BusLogic in the form of 16 separate
  6. source files, which would have unnecessarily cluttered the scsi directory, so
  7. the individual files have been combined into this single file.
  8. Copyright 1995-1996 by Mylex Corporation. All Rights Reserved
  9. This file is available under both the GNU General Public License
  10. and a BSD-style copyright; see LICENSE.FlashPoint for details.
  11. */
  12. #ifdef CONFIG_SCSI_FLASHPOINT
  13. #define MAX_CARDS 8
  14. #undef BUSTYPE_PCI
  15. #define CRCMASK 0xA001
  16. #define FAILURE 0xFFFFFFFFL
  17. struct sccb;
  18. typedef void (*CALL_BK_FN) (struct sccb *);
  19. struct sccb_mgr_info {
  20. u32 si_baseaddr;
  21. unsigned char si_present;
  22. unsigned char si_intvect;
  23. unsigned char si_id;
  24. unsigned char si_lun;
  25. u16 si_fw_revision;
  26. u16 si_per_targ_init_sync;
  27. u16 si_per_targ_fast_nego;
  28. u16 si_per_targ_ultra_nego;
  29. u16 si_per_targ_no_disc;
  30. u16 si_per_targ_wide_nego;
  31. u16 si_flags;
  32. unsigned char si_card_family;
  33. unsigned char si_bustype;
  34. unsigned char si_card_model[3];
  35. unsigned char si_relative_cardnum;
  36. unsigned char si_reserved[4];
  37. u32 si_OS_reserved;
  38. unsigned char si_XlatInfo[4];
  39. u32 si_reserved2[5];
  40. u32 si_secondary_range;
  41. };
  42. #define SCSI_PARITY_ENA 0x0001
  43. #define LOW_BYTE_TERM 0x0010
  44. #define HIGH_BYTE_TERM 0x0020
  45. #define BUSTYPE_PCI 0x3
  46. #define SUPPORT_16TAR_32LUN 0x0002
  47. #define SOFT_RESET 0x0004
  48. #define EXTENDED_TRANSLATION 0x0008
  49. #define POST_ALL_UNDERRRUNS 0x0040
  50. #define FLAG_SCAM_ENABLED 0x0080
  51. #define FLAG_SCAM_LEVEL2 0x0100
  52. #define HARPOON_FAMILY 0x02
  53. /* SCCB struct used for both SCCB and UCB manager compiles!
  54. * The UCB Manager treats the SCCB as it's 'native hardware structure'
  55. */
  56. /*#pragma pack(1)*/
  57. struct sccb {
  58. unsigned char OperationCode;
  59. unsigned char ControlByte;
  60. unsigned char CdbLength;
  61. unsigned char RequestSenseLength;
  62. u32 DataLength;
  63. void *DataPointer;
  64. unsigned char CcbRes[2];
  65. unsigned char HostStatus;
  66. unsigned char TargetStatus;
  67. unsigned char TargID;
  68. unsigned char Lun;
  69. unsigned char Cdb[12];
  70. unsigned char CcbRes1;
  71. unsigned char Reserved1;
  72. u32 Reserved2;
  73. u32 SensePointer;
  74. CALL_BK_FN SccbCallback; /* VOID (*SccbCallback)(); */
  75. u32 SccbIOPort; /* Identifies board base port */
  76. unsigned char SccbStatus;
  77. unsigned char SCCBRes2;
  78. u16 SccbOSFlags;
  79. u32 Sccb_XferCnt; /* actual transfer count */
  80. u32 Sccb_ATC;
  81. u32 SccbVirtDataPtr; /* virtual addr for OS/2 */
  82. u32 Sccb_res1;
  83. u16 Sccb_MGRFlags;
  84. u16 Sccb_sgseg;
  85. unsigned char Sccb_scsimsg; /* identify msg for selection */
  86. unsigned char Sccb_tag;
  87. unsigned char Sccb_scsistat;
  88. unsigned char Sccb_idmsg; /* image of last msg in */
  89. struct sccb *Sccb_forwardlink;
  90. struct sccb *Sccb_backlink;
  91. u32 Sccb_savedATC;
  92. unsigned char Save_Cdb[6];
  93. unsigned char Save_CdbLen;
  94. unsigned char Sccb_XferState;
  95. u32 Sccb_SGoffset;
  96. };
  97. #pragma pack()
  98. #define SCATTER_GATHER_COMMAND 0x02
  99. #define RESIDUAL_COMMAND 0x03
  100. #define RESIDUAL_SG_COMMAND 0x04
  101. #define RESET_COMMAND 0x81
  102. #define F_USE_CMD_Q 0x20 /*Inidcates TAGGED command. */
  103. #define TAG_TYPE_MASK 0xC0 /*Type of tag msg to send. */
  104. #define SCCB_DATA_XFER_OUT 0x10 /* Write */
  105. #define SCCB_DATA_XFER_IN 0x08 /* Read */
  106. #define NO_AUTO_REQUEST_SENSE 0x01 /* No Request Sense Buffer */
  107. #define BUS_FREE_ST 0
  108. #define SELECT_ST 1
  109. #define SELECT_BDR_ST 2 /* Select w\ Bus Device Reset */
  110. #define SELECT_SN_ST 3 /* Select w\ Sync Nego */
  111. #define SELECT_WN_ST 4 /* Select w\ Wide Data Nego */
  112. #define SELECT_Q_ST 5 /* Select w\ Tagged Q'ing */
  113. #define COMMAND_ST 6
  114. #define DATA_OUT_ST 7
  115. #define DATA_IN_ST 8
  116. #define DISCONNECT_ST 9
  117. #define ABORT_ST 11
  118. #define F_HOST_XFER_DIR 0x01
  119. #define F_ALL_XFERRED 0x02
  120. #define F_SG_XFER 0x04
  121. #define F_AUTO_SENSE 0x08
  122. #define F_ODD_BALL_CNT 0x10
  123. #define F_NO_DATA_YET 0x80
  124. #define F_STATUSLOADED 0x01
  125. #define F_DEV_SELECTED 0x04
  126. #define SCCB_COMPLETE 0x00 /* SCCB completed without error */
  127. #define SCCB_DATA_UNDER_RUN 0x0C
  128. #define SCCB_SELECTION_TIMEOUT 0x11 /* Set SCSI selection timed out */
  129. #define SCCB_DATA_OVER_RUN 0x12
  130. #define SCCB_PHASE_SEQUENCE_FAIL 0x14 /* Target bus phase sequence failure */
  131. #define SCCB_GROSS_FW_ERR 0x27 /* Major problem! */
  132. #define SCCB_BM_ERR 0x30 /* BusMaster error. */
  133. #define SCCB_PARITY_ERR 0x34 /* SCSI parity error */
  134. #define SCCB_IN_PROCESS 0x00
  135. #define SCCB_SUCCESS 0x01
  136. #define SCCB_ABORT 0x02
  137. #define SCCB_ERROR 0x04
  138. #define ORION_FW_REV 3110
  139. #define QUEUE_DEPTH 254+1 /*1 for Normal disconnect 32 for Q'ing. */
  140. #define MAX_MB_CARDS 4 /* Max. no of cards suppoerted on Mother Board */
  141. #define MAX_SCSI_TAR 16
  142. #define MAX_LUN 32
  143. #define LUN_MASK 0x1f
  144. #define SG_BUF_CNT 16 /*Number of prefetched elements. */
  145. #define SG_ELEMENT_SIZE 8 /*Eight byte per element. */
  146. #define RD_HARPOON(ioport) inb((u32)ioport)
  147. #define RDW_HARPOON(ioport) inw((u32)ioport)
  148. #define RD_HARP32(ioport,offset,data) (data = inl((u32)(ioport + offset)))
  149. #define WR_HARPOON(ioport,val) outb((u8) val, (u32)ioport)
  150. #define WRW_HARPOON(ioport,val) outw((u16)val, (u32)ioport)
  151. #define WR_HARP32(ioport,offset,data) outl(data, (u32)(ioport + offset))
  152. #define TAR_SYNC_MASK (BIT(7)+BIT(6))
  153. #define SYNC_TRYING BIT(6)
  154. #define SYNC_SUPPORTED (BIT(7)+BIT(6))
  155. #define TAR_WIDE_MASK (BIT(5)+BIT(4))
  156. #define WIDE_ENABLED BIT(4)
  157. #define WIDE_NEGOCIATED BIT(5)
  158. #define TAR_TAG_Q_MASK (BIT(3)+BIT(2))
  159. #define TAG_Q_TRYING BIT(2)
  160. #define TAG_Q_REJECT BIT(3)
  161. #define TAR_ALLOW_DISC BIT(0)
  162. #define EE_SYNC_MASK (BIT(0)+BIT(1))
  163. #define EE_SYNC_5MB BIT(0)
  164. #define EE_SYNC_10MB BIT(1)
  165. #define EE_SYNC_20MB (BIT(0)+BIT(1))
  166. #define EE_WIDE_SCSI BIT(7)
  167. struct sccb_mgr_tar_info {
  168. struct sccb *TarSelQ_Head;
  169. struct sccb *TarSelQ_Tail;
  170. unsigned char TarLUN_CA; /*Contingent Allgiance */
  171. unsigned char TarTagQ_Cnt;
  172. unsigned char TarSelQ_Cnt;
  173. unsigned char TarStatus;
  174. unsigned char TarEEValue;
  175. unsigned char TarSyncCtrl;
  176. unsigned char TarReserved[2]; /* for alignment */
  177. unsigned char LunDiscQ_Idx[MAX_LUN];
  178. unsigned char TarLUNBusy[MAX_LUN];
  179. };
  180. struct nvram_info {
  181. unsigned char niModel; /* Model No. of card */
  182. unsigned char niCardNo; /* Card no. */
  183. u32 niBaseAddr; /* Port Address of card */
  184. unsigned char niSysConf; /* Adapter Configuration byte -
  185. Byte 16 of eeprom map */
  186. unsigned char niScsiConf; /* SCSI Configuration byte -
  187. Byte 17 of eeprom map */
  188. unsigned char niScamConf; /* SCAM Configuration byte -
  189. Byte 20 of eeprom map */
  190. unsigned char niAdapId; /* Host Adapter ID -
  191. Byte 24 of eerpom map */
  192. unsigned char niSyncTbl[MAX_SCSI_TAR / 2]; /* Sync/Wide byte
  193. of targets */
  194. unsigned char niScamTbl[MAX_SCSI_TAR][4]; /* Compressed Scam name
  195. string of Targets */
  196. };
  197. #define MODEL_LT 1
  198. #define MODEL_DL 2
  199. #define MODEL_LW 3
  200. #define MODEL_DW 4
  201. struct sccb_card {
  202. struct sccb *currentSCCB;
  203. struct sccb_mgr_info *cardInfo;
  204. u32 ioPort;
  205. unsigned short cmdCounter;
  206. unsigned char discQCount;
  207. unsigned char tagQ_Lst;
  208. unsigned char cardIndex;
  209. unsigned char scanIndex;
  210. unsigned char globalFlags;
  211. unsigned char ourId;
  212. struct nvram_info *pNvRamInfo;
  213. struct sccb *discQ_Tbl[QUEUE_DEPTH];
  214. };
  215. #define F_TAG_STARTED 0x01
  216. #define F_CONLUN_IO 0x02
  217. #define F_DO_RENEGO 0x04
  218. #define F_NO_FILTER 0x08
  219. #define F_GREEN_PC 0x10
  220. #define F_HOST_XFER_ACT 0x20
  221. #define F_NEW_SCCB_CMD 0x40
  222. #define F_UPDATE_EEPROM 0x80
  223. #define ID_STRING_LENGTH 32
  224. #define TYPE_CODE0 0x63 /*Level2 Mstr (bits 7-6), */
  225. #define SLV_TYPE_CODE0 0xA3 /*Priority Bit set (bits 7-6), */
  226. #define ASSIGN_ID 0x00
  227. #define SET_P_FLAG 0x01
  228. #define CFG_CMPLT 0x03
  229. #define DOM_MSTR 0x0F
  230. #define SYNC_PTRN 0x1F
  231. #define ID_0_7 0x18
  232. #define ID_8_F 0x11
  233. #define MISC_CODE 0x14
  234. #define CLR_P_FLAG 0x18
  235. #define INIT_SELTD 0x01
  236. #define LEVEL2_TAR 0x02
  237. enum scam_id_st { ID0, ID1, ID2, ID3, ID4, ID5, ID6, ID7, ID8, ID9, ID10, ID11,
  238. ID12,
  239. ID13, ID14, ID15, ID_UNUSED, ID_UNASSIGNED, ID_ASSIGNED, LEGACY,
  240. CLR_PRIORITY, NO_ID_AVAIL
  241. };
  242. typedef struct SCCBscam_info {
  243. unsigned char id_string[ID_STRING_LENGTH];
  244. enum scam_id_st state;
  245. } SCCBSCAM_INFO;
  246. #define SCSI_REQUEST_SENSE 0x03
  247. #define SCSI_READ 0x08
  248. #define SCSI_WRITE 0x0A
  249. #define SCSI_START_STOP_UNIT 0x1B
  250. #define SCSI_READ_EXTENDED 0x28
  251. #define SCSI_WRITE_EXTENDED 0x2A
  252. #define SCSI_WRITE_AND_VERIFY 0x2E
  253. #define SSGOOD 0x00
  254. #define SSCHECK 0x02
  255. #define SSQ_FULL 0x28
  256. #define SMCMD_COMP 0x00
  257. #define SMEXT 0x01
  258. #define SMSAVE_DATA_PTR 0x02
  259. #define SMREST_DATA_PTR 0x03
  260. #define SMDISC 0x04
  261. #define SMABORT 0x06
  262. #define SMREJECT 0x07
  263. #define SMNO_OP 0x08
  264. #define SMPARITY 0x09
  265. #define SMDEV_RESET 0x0C
  266. #define SMABORT_TAG 0x0D
  267. #define SMINIT_RECOVERY 0x0F
  268. #define SMREL_RECOVERY 0x10
  269. #define SMIDENT 0x80
  270. #define DISC_PRIV 0x40
  271. #define SMSYNC 0x01
  272. #define SMWDTR 0x03
  273. #define SM8BIT 0x00
  274. #define SM16BIT 0x01
  275. #define SMIGNORWR 0x23 /* Ignore Wide Residue */
  276. #define SIX_BYTE_CMD 0x06
  277. #define TWELVE_BYTE_CMD 0x0C
  278. #define ASYNC 0x00
  279. #define MAX_OFFSET 0x0F /* Maxbyteoffset for Sync Xfers */
  280. #define EEPROM_WD_CNT 256
  281. #define EEPROM_CHECK_SUM 0
  282. #define FW_SIGNATURE 2
  283. #define MODEL_NUMB_0 4
  284. #define MODEL_NUMB_2 6
  285. #define MODEL_NUMB_4 8
  286. #define SYSTEM_CONFIG 16
  287. #define SCSI_CONFIG 17
  288. #define BIOS_CONFIG 18
  289. #define SCAM_CONFIG 20
  290. #define ADAPTER_SCSI_ID 24
  291. #define IGNORE_B_SCAN 32
  292. #define SEND_START_ENA 34
  293. #define DEVICE_ENABLE 36
  294. #define SYNC_RATE_TBL 38
  295. #define SYNC_RATE_TBL01 38
  296. #define SYNC_RATE_TBL23 40
  297. #define SYNC_RATE_TBL45 42
  298. #define SYNC_RATE_TBL67 44
  299. #define SYNC_RATE_TBL89 46
  300. #define SYNC_RATE_TBLab 48
  301. #define SYNC_RATE_TBLcd 50
  302. #define SYNC_RATE_TBLef 52
  303. #define EE_SCAMBASE 256
  304. #define SCAM_ENABLED BIT(2)
  305. #define SCAM_LEVEL2 BIT(3)
  306. #define RENEGO_ENA BIT(10)
  307. #define CONNIO_ENA BIT(11)
  308. #define GREEN_PC_ENA BIT(12)
  309. #define AUTO_RATE_00 00
  310. #define AUTO_RATE_05 01
  311. #define AUTO_RATE_10 02
  312. #define AUTO_RATE_20 03
  313. #define WIDE_NEGO_BIT BIT(7)
  314. #define DISC_ENABLE_BIT BIT(6)
  315. #define hp_vendor_id_0 0x00 /* LSB */
  316. #define ORION_VEND_0 0x4B
  317. #define hp_vendor_id_1 0x01 /* MSB */
  318. #define ORION_VEND_1 0x10
  319. #define hp_device_id_0 0x02 /* LSB */
  320. #define ORION_DEV_0 0x30
  321. #define hp_device_id_1 0x03 /* MSB */
  322. #define ORION_DEV_1 0x81
  323. /* Sub Vendor ID and Sub Device ID only available in
  324. Harpoon Version 2 and higher */
  325. #define hp_sub_device_id_0 0x06 /* LSB */
  326. #define hp_semaphore 0x0C
  327. #define SCCB_MGR_ACTIVE BIT(0)
  328. #define TICKLE_ME BIT(1)
  329. #define SCCB_MGR_PRESENT BIT(3)
  330. #define BIOS_IN_USE BIT(4)
  331. #define hp_sys_ctrl 0x0F
  332. #define STOP_CLK BIT(0) /*Turn off BusMaster Clock */
  333. #define DRVR_RST BIT(1) /*Firmware Reset to 80C15 chip */
  334. #define HALT_MACH BIT(3) /*Halt State Machine */
  335. #define HARD_ABORT BIT(4) /*Hard Abort */
  336. #define hp_host_blk_cnt 0x13
  337. #define XFER_BLK64 0x06 /* 1 1 0 64 byte per block */
  338. #define BM_THRESHOLD 0x40 /* PCI mode can only xfer 16 bytes */
  339. #define hp_int_mask 0x17
  340. #define INT_CMD_COMPL BIT(0) /* DMA command complete */
  341. #define INT_EXT_STATUS BIT(1) /* Extended Status Set */
  342. #define hp_xfer_cnt_lo 0x18
  343. #define hp_xfer_cnt_hi 0x1A
  344. #define hp_xfer_cmd 0x1B
  345. #define XFER_HOST_DMA 0x00 /* 0 0 0 Transfer Host -> DMA */
  346. #define XFER_DMA_HOST 0x01 /* 0 0 1 Transfer DMA -> Host */
  347. #define XFER_HOST_AUTO 0x00 /* 0 0 Auto Transfer Size */
  348. #define XFER_DMA_8BIT 0x20 /* 0 1 8 BIT Transfer Size */
  349. #define DISABLE_INT BIT(7) /*Do not interrupt at end of cmd. */
  350. #define HOST_WRT_CMD ((DISABLE_INT + XFER_HOST_DMA + XFER_HOST_AUTO + XFER_DMA_8BIT))
  351. #define HOST_RD_CMD ((DISABLE_INT + XFER_DMA_HOST + XFER_HOST_AUTO + XFER_DMA_8BIT))
  352. #define hp_host_addr_lo 0x1C
  353. #define hp_host_addr_hmi 0x1E
  354. #define hp_ee_ctrl 0x22
  355. #define EXT_ARB_ACK BIT(7)
  356. #define SCSI_TERM_ENA_H BIT(6) /* SCSI high byte terminator */
  357. #define SEE_MS BIT(5)
  358. #define SEE_CS BIT(3)
  359. #define SEE_CLK BIT(2)
  360. #define SEE_DO BIT(1)
  361. #define SEE_DI BIT(0)
  362. #define EE_READ 0x06
  363. #define EE_WRITE 0x05
  364. #define EWEN 0x04
  365. #define EWEN_ADDR 0x03C0
  366. #define EWDS 0x04
  367. #define EWDS_ADDR 0x0000
  368. #define hp_bm_ctrl 0x26
  369. #define SCSI_TERM_ENA_L BIT(0) /*Enable/Disable external terminators */
  370. #define FLUSH_XFER_CNTR BIT(1) /*Flush transfer counter */
  371. #define FORCE1_XFER BIT(5) /*Always xfer one byte in byte mode */
  372. #define FAST_SINGLE BIT(6) /*?? */
  373. #define BMCTRL_DEFAULT (FORCE1_XFER|FAST_SINGLE|SCSI_TERM_ENA_L)
  374. #define hp_sg_addr 0x28
  375. #define hp_page_ctrl 0x29
  376. #define SCATTER_EN BIT(0)
  377. #define SGRAM_ARAM BIT(1)
  378. #define G_INT_DISABLE BIT(3) /* Enable/Disable all Interrupts */
  379. #define NARROW_SCSI_CARD BIT(4) /* NARROW/WIDE SCSI config pin */
  380. #define hp_pci_stat_cfg 0x2D
  381. #define REC_MASTER_ABORT BIT(5) /*received Master abort */
  382. #define hp_rev_num 0x33
  383. #define hp_stack_data 0x34
  384. #define hp_stack_addr 0x35
  385. #define hp_ext_status 0x36
  386. #define BM_FORCE_OFF BIT(0) /*Bus Master is forced to get off */
  387. #define PCI_TGT_ABORT BIT(0) /*PCI bus master transaction aborted */
  388. #define PCI_DEV_TMOUT BIT(1) /*PCI Device Time out */
  389. #define CMD_ABORTED BIT(4) /*Command aborted */
  390. #define BM_PARITY_ERR BIT(5) /*parity error on data received */
  391. #define PIO_OVERRUN BIT(6) /*Slave data overrun */
  392. #define BM_CMD_BUSY BIT(7) /*Bus master transfer command busy */
  393. #define BAD_EXT_STATUS (BM_FORCE_OFF | PCI_DEV_TMOUT | CMD_ABORTED | \
  394. BM_PARITY_ERR | PIO_OVERRUN)
  395. #define hp_int_status 0x37
  396. #define EXT_STATUS_ON BIT(1) /*Extended status is valid */
  397. #define SCSI_INTERRUPT BIT(2) /*Global indication of a SCSI int. */
  398. #define INT_ASSERTED BIT(5) /* */
  399. #define hp_fifo_cnt 0x38
  400. #define hp_intena 0x40
  401. #define RESET BIT(7)
  402. #define PROG_HLT BIT(6)
  403. #define PARITY BIT(5)
  404. #define FIFO BIT(4)
  405. #define SEL BIT(3)
  406. #define SCAM_SEL BIT(2)
  407. #define RSEL BIT(1)
  408. #define TIMEOUT BIT(0)
  409. #define BUS_FREE BIT(15)
  410. #define XFER_CNT_0 BIT(14)
  411. #define PHASE BIT(13)
  412. #define IUNKWN BIT(12)
  413. #define ICMD_COMP BIT(11)
  414. #define ITICKLE BIT(10)
  415. #define IDO_STRT BIT(9)
  416. #define ITAR_DISC BIT(8)
  417. #define AUTO_INT (BIT(12)+BIT(11)+BIT(10)+BIT(9)+BIT(8))
  418. #define CLR_ALL_INT 0xFFFF
  419. #define CLR_ALL_INT_1 0xFF00
  420. #define hp_intstat 0x42
  421. #define hp_scsisig 0x44
  422. #define SCSI_SEL BIT(7)
  423. #define SCSI_BSY BIT(6)
  424. #define SCSI_REQ BIT(5)
  425. #define SCSI_ACK BIT(4)
  426. #define SCSI_ATN BIT(3)
  427. #define SCSI_CD BIT(2)
  428. #define SCSI_MSG BIT(1)
  429. #define SCSI_IOBIT BIT(0)
  430. #define S_SCSI_PHZ (BIT(2)+BIT(1)+BIT(0))
  431. #define S_MSGO_PH (BIT(2)+BIT(1) )
  432. #define S_MSGI_PH (BIT(2)+BIT(1)+BIT(0))
  433. #define S_DATAI_PH ( BIT(0))
  434. #define S_DATAO_PH 0x00
  435. #define S_ILL_PH ( BIT(1) )
  436. #define hp_scsictrl_0 0x45
  437. #define SEL_TAR BIT(6)
  438. #define ENA_ATN BIT(4)
  439. #define ENA_RESEL BIT(2)
  440. #define SCSI_RST BIT(1)
  441. #define ENA_SCAM_SEL BIT(0)
  442. #define hp_portctrl_0 0x46
  443. #define SCSI_PORT BIT(7)
  444. #define SCSI_INBIT BIT(6)
  445. #define DMA_PORT BIT(5)
  446. #define DMA_RD BIT(4)
  447. #define HOST_PORT BIT(3)
  448. #define HOST_WRT BIT(2)
  449. #define SCSI_BUS_EN BIT(1)
  450. #define START_TO BIT(0)
  451. #define hp_scsireset 0x47
  452. #define SCSI_INI BIT(6)
  453. #define SCAM_EN BIT(5)
  454. #define DMA_RESET BIT(3)
  455. #define HPSCSI_RESET BIT(2)
  456. #define PROG_RESET BIT(1)
  457. #define FIFO_CLR BIT(0)
  458. #define hp_xfercnt_0 0x48
  459. #define hp_xfercnt_2 0x4A
  460. #define hp_fifodata_0 0x4C
  461. #define hp_addstat 0x4E
  462. #define SCAM_TIMER BIT(7)
  463. #define SCSI_MODE8 BIT(3)
  464. #define SCSI_PAR_ERR BIT(0)
  465. #define hp_prgmcnt_0 0x4F
  466. #define hp_selfid_0 0x50
  467. #define hp_selfid_1 0x51
  468. #define hp_arb_id 0x52
  469. #define hp_select_id 0x53
  470. #define hp_synctarg_base 0x54
  471. #define hp_synctarg_12 0x54
  472. #define hp_synctarg_13 0x55
  473. #define hp_synctarg_14 0x56
  474. #define hp_synctarg_15 0x57
  475. #define hp_synctarg_8 0x58
  476. #define hp_synctarg_9 0x59
  477. #define hp_synctarg_10 0x5A
  478. #define hp_synctarg_11 0x5B
  479. #define hp_synctarg_4 0x5C
  480. #define hp_synctarg_5 0x5D
  481. #define hp_synctarg_6 0x5E
  482. #define hp_synctarg_7 0x5F
  483. #define hp_synctarg_0 0x60
  484. #define hp_synctarg_1 0x61
  485. #define hp_synctarg_2 0x62
  486. #define hp_synctarg_3 0x63
  487. #define NARROW_SCSI BIT(4)
  488. #define DEFAULT_OFFSET 0x0F
  489. #define hp_autostart_0 0x64
  490. #define hp_autostart_1 0x65
  491. #define hp_autostart_3 0x67
  492. #define AUTO_IMMED BIT(5)
  493. #define SELECT BIT(6)
  494. #define END_DATA (BIT(7)+BIT(6))
  495. #define hp_gp_reg_0 0x68
  496. #define hp_gp_reg_1 0x69
  497. #define hp_gp_reg_3 0x6B
  498. #define hp_seltimeout 0x6C
  499. #define TO_4ms 0x67 /* 3.9959ms */
  500. #define TO_5ms 0x03 /* 4.9152ms */
  501. #define TO_10ms 0x07 /* 11.xxxms */
  502. #define TO_250ms 0x99 /* 250.68ms */
  503. #define TO_290ms 0xB1 /* 289.99ms */
  504. #define hp_clkctrl_0 0x6D
  505. #define PWR_DWN BIT(6)
  506. #define ACTdeassert BIT(4)
  507. #define CLK_40MHZ (BIT(1) + BIT(0))
  508. #define CLKCTRL_DEFAULT (ACTdeassert | CLK_40MHZ)
  509. #define hp_fiforead 0x6E
  510. #define hp_fifowrite 0x6F
  511. #define hp_offsetctr 0x70
  512. #define hp_xferstat 0x71
  513. #define FIFO_EMPTY BIT(6)
  514. #define hp_portctrl_1 0x72
  515. #define CHK_SCSI_P BIT(3)
  516. #define HOST_MODE8 BIT(0)
  517. #define hp_xfer_pad 0x73
  518. #define ID_UNLOCK BIT(3)
  519. #define hp_scsidata_0 0x74
  520. #define hp_scsidata_1 0x75
  521. #define hp_aramBase 0x80
  522. #define BIOS_DATA_OFFSET 0x60
  523. #define BIOS_RELATIVE_CARD 0x64
  524. #define AR3 (BIT(9) + BIT(8))
  525. #define SDATA BIT(10)
  526. #define CRD_OP BIT(11) /* Cmp Reg. w/ Data */
  527. #define CRR_OP BIT(12) /* Cmp Reg. w. Reg. */
  528. #define CPE_OP (BIT(14)+BIT(11)) /* Cmp SCSI phs & Branch EQ */
  529. #define CPN_OP (BIT(14)+BIT(12)) /* Cmp SCSI phs & Branch NOT EQ */
  530. #define ADATA_OUT 0x00
  531. #define ADATA_IN BIT(8)
  532. #define ACOMMAND BIT(10)
  533. #define ASTATUS (BIT(10)+BIT(8))
  534. #define AMSG_OUT (BIT(10)+BIT(9))
  535. #define AMSG_IN (BIT(10)+BIT(9)+BIT(8))
  536. #define BRH_OP BIT(13) /* Branch */
  537. #define ALWAYS 0x00
  538. #define EQUAL BIT(8)
  539. #define NOT_EQ BIT(9)
  540. #define TCB_OP (BIT(13)+BIT(11)) /* Test condition & branch */
  541. #define FIFO_0 BIT(10)
  542. #define MPM_OP BIT(15) /* Match phase and move data */
  543. #define MRR_OP BIT(14) /* Move DReg. to Reg. */
  544. #define S_IDREG (BIT(2)+BIT(1)+BIT(0))
  545. #define D_AR0 0x00
  546. #define D_AR1 BIT(0)
  547. #define D_BUCKET (BIT(2) + BIT(1) + BIT(0))
  548. #define RAT_OP (BIT(14)+BIT(13)+BIT(11))
  549. #define SSI_OP (BIT(15)+BIT(11))
  550. #define SSI_ITAR_DISC (ITAR_DISC >> 8)
  551. #define SSI_IDO_STRT (IDO_STRT >> 8)
  552. #define SSI_ICMD_COMP (ICMD_COMP >> 8)
  553. #define SSI_ITICKLE (ITICKLE >> 8)
  554. #define SSI_IUNKWN (IUNKWN >> 8)
  555. #define SSI_INO_CC (IUNKWN >> 8)
  556. #define SSI_IRFAIL (IUNKWN >> 8)
  557. #define NP 0x10 /*Next Phase */
  558. #define NTCMD 0x02 /*Non- Tagged Command start */
  559. #define CMDPZ 0x04 /*Command phase */
  560. #define DINT 0x12 /*Data Out/In interrupt */
  561. #define DI 0x13 /*Data Out */
  562. #define DC 0x19 /*Disconnect Message */
  563. #define ST 0x1D /*Status Phase */
  564. #define UNKNWN 0x24 /*Unknown bus action */
  565. #define CC 0x25 /*Command Completion failure */
  566. #define TICK 0x26 /*New target reselected us. */
  567. #define SELCHK 0x28 /*Select & Check SCSI ID latch reg */
  568. #define ID_MSG_STRT hp_aramBase + 0x00
  569. #define NON_TAG_ID_MSG hp_aramBase + 0x06
  570. #define CMD_STRT hp_aramBase + 0x08
  571. #define SYNC_MSGS hp_aramBase + 0x08
  572. #define TAG_STRT 0x00
  573. #define DISCONNECT_START 0x10/2
  574. #define END_DATA_START 0x14/2
  575. #define CMD_ONLY_STRT CMDPZ/2
  576. #define SELCHK_STRT SELCHK/2
  577. #define GET_XFER_CNT(port, xfercnt) {RD_HARP32(port,hp_xfercnt_0,xfercnt); xfercnt &= 0xFFFFFF;}
  578. /* #define GET_XFER_CNT(port, xfercnt) (xfercnt = RD_HARPOON(port+hp_xfercnt_2), \
  579. xfercnt <<= 16,\
  580. xfercnt |= RDW_HARPOON((unsigned short)(port+hp_xfercnt_0)))
  581. */
  582. #define HP_SETUP_ADDR_CNT(port,addr,count) (WRW_HARPOON((port+hp_host_addr_lo), (unsigned short)(addr & 0x0000FFFFL)),\
  583. addr >>= 16,\
  584. WRW_HARPOON((port+hp_host_addr_hmi), (unsigned short)(addr & 0x0000FFFFL)),\
  585. WR_HARP32(port,hp_xfercnt_0,count),\
  586. WRW_HARPOON((port+hp_xfer_cnt_lo), (unsigned short)(count & 0x0000FFFFL)),\
  587. count >>= 16,\
  588. WR_HARPOON(port+hp_xfer_cnt_hi, (count & 0xFF)))
  589. #define ACCEPT_MSG(port) {while(RD_HARPOON(port+hp_scsisig) & SCSI_REQ){}\
  590. WR_HARPOON(port+hp_scsisig, S_ILL_PH);}
  591. #define ACCEPT_MSG_ATN(port) {while(RD_HARPOON(port+hp_scsisig) & SCSI_REQ){}\
  592. WR_HARPOON(port+hp_scsisig, (S_ILL_PH|SCSI_ATN));}
  593. #define DISABLE_AUTO(port) (WR_HARPOON(port+hp_scsireset, PROG_RESET),\
  594. WR_HARPOON(port+hp_scsireset, 0x00))
  595. #define ARAM_ACCESS(p_port) (WR_HARPOON(p_port+hp_page_ctrl, \
  596. (RD_HARPOON(p_port+hp_page_ctrl) | SGRAM_ARAM)))
  597. #define SGRAM_ACCESS(p_port) (WR_HARPOON(p_port+hp_page_ctrl, \
  598. (RD_HARPOON(p_port+hp_page_ctrl) & ~SGRAM_ARAM)))
  599. #define MDISABLE_INT(p_port) (WR_HARPOON(p_port+hp_page_ctrl, \
  600. (RD_HARPOON(p_port+hp_page_ctrl) | G_INT_DISABLE)))
  601. #define MENABLE_INT(p_port) (WR_HARPOON(p_port+hp_page_ctrl, \
  602. (RD_HARPOON(p_port+hp_page_ctrl) & ~G_INT_DISABLE)))
  603. static unsigned char FPT_sisyncn(u32 port, unsigned char p_card,
  604. unsigned char syncFlag);
  605. static void FPT_ssel(u32 port, unsigned char p_card);
  606. static void FPT_sres(u32 port, unsigned char p_card,
  607. struct sccb_card *pCurrCard);
  608. static void FPT_shandem(u32 port, unsigned char p_card,
  609. struct sccb *pCurrSCCB);
  610. static void FPT_stsyncn(u32 port, unsigned char p_card);
  611. static void FPT_sisyncr(u32 port, unsigned char sync_pulse,
  612. unsigned char offset);
  613. static void FPT_sssyncv(u32 p_port, unsigned char p_id,
  614. unsigned char p_sync_value,
  615. struct sccb_mgr_tar_info *currTar_Info);
  616. static void FPT_sresb(u32 port, unsigned char p_card);
  617. static void FPT_sxfrp(u32 p_port, unsigned char p_card);
  618. static void FPT_schkdd(u32 port, unsigned char p_card);
  619. static unsigned char FPT_RdStack(u32 port, unsigned char index);
  620. static void FPT_WrStack(u32 portBase, unsigned char index,
  621. unsigned char data);
  622. static unsigned char FPT_ChkIfChipInitialized(u32 ioPort);
  623. static void FPT_SendMsg(u32 port, unsigned char message);
  624. static void FPT_queueFlushTargSccb(unsigned char p_card, unsigned char thisTarg,
  625. unsigned char error_code);
  626. static void FPT_sinits(struct sccb *p_sccb, unsigned char p_card);
  627. static void FPT_RNVRamData(struct nvram_info *pNvRamInfo);
  628. static unsigned char FPT_siwidn(u32 port, unsigned char p_card);
  629. static void FPT_stwidn(u32 port, unsigned char p_card);
  630. static void FPT_siwidr(u32 port, unsigned char width);
  631. static void FPT_queueSelectFail(struct sccb_card *pCurrCard,
  632. unsigned char p_card);
  633. static void FPT_queueDisconnect(struct sccb *p_SCCB, unsigned char p_card);
  634. static void FPT_queueCmdComplete(struct sccb_card *pCurrCard,
  635. struct sccb *p_SCCB, unsigned char p_card);
  636. static void FPT_queueSearchSelect(struct sccb_card *pCurrCard,
  637. unsigned char p_card);
  638. static void FPT_queueFlushSccb(unsigned char p_card, unsigned char error_code);
  639. static void FPT_queueAddSccb(struct sccb *p_SCCB, unsigned char card);
  640. static unsigned char FPT_queueFindSccb(struct sccb *p_SCCB,
  641. unsigned char p_card);
  642. static void FPT_utilUpdateResidual(struct sccb *p_SCCB);
  643. static unsigned short FPT_CalcCrc16(unsigned char buffer[]);
  644. static unsigned char FPT_CalcLrc(unsigned char buffer[]);
  645. static void FPT_Wait1Second(u32 p_port);
  646. static void FPT_Wait(u32 p_port, unsigned char p_delay);
  647. static void FPT_utilEEWriteOnOff(u32 p_port, unsigned char p_mode);
  648. static void FPT_utilEEWrite(u32 p_port, unsigned short ee_data,
  649. unsigned short ee_addr);
  650. static unsigned short FPT_utilEERead(u32 p_port,
  651. unsigned short ee_addr);
  652. static unsigned short FPT_utilEEReadOrg(u32 p_port,
  653. unsigned short ee_addr);
  654. static void FPT_utilEESendCmdAddr(u32 p_port, unsigned char ee_cmd,
  655. unsigned short ee_addr);
  656. static void FPT_phaseDataOut(u32 port, unsigned char p_card);
  657. static void FPT_phaseDataIn(u32 port, unsigned char p_card);
  658. static void FPT_phaseCommand(u32 port, unsigned char p_card);
  659. static void FPT_phaseStatus(u32 port, unsigned char p_card);
  660. static void FPT_phaseMsgOut(u32 port, unsigned char p_card);
  661. static void FPT_phaseMsgIn(u32 port, unsigned char p_card);
  662. static void FPT_phaseIllegal(u32 port, unsigned char p_card);
  663. static void FPT_phaseDecode(u32 port, unsigned char p_card);
  664. static void FPT_phaseChkFifo(u32 port, unsigned char p_card);
  665. static void FPT_phaseBusFree(u32 p_port, unsigned char p_card);
  666. static void FPT_XbowInit(u32 port, unsigned char scamFlg);
  667. static void FPT_BusMasterInit(u32 p_port);
  668. static void FPT_DiagEEPROM(u32 p_port);
  669. static void FPT_dataXferProcessor(u32 port,
  670. struct sccb_card *pCurrCard);
  671. static void FPT_busMstrSGDataXferStart(u32 port,
  672. struct sccb *pCurrSCCB);
  673. static void FPT_busMstrDataXferStart(u32 port,
  674. struct sccb *pCurrSCCB);
  675. static void FPT_hostDataXferAbort(u32 port, unsigned char p_card,
  676. struct sccb *pCurrSCCB);
  677. static void FPT_hostDataXferRestart(struct sccb *currSCCB);
  678. static unsigned char FPT_SccbMgr_bad_isr(u32 p_port,
  679. unsigned char p_card,
  680. struct sccb_card *pCurrCard,
  681. unsigned short p_int);
  682. static void FPT_SccbMgrTableInitAll(void);
  683. static void FPT_SccbMgrTableInitCard(struct sccb_card *pCurrCard,
  684. unsigned char p_card);
  685. static void FPT_SccbMgrTableInitTarget(unsigned char p_card,
  686. unsigned char target);
  687. static void FPT_scini(unsigned char p_card, unsigned char p_our_id,
  688. unsigned char p_power_up);
  689. static int FPT_scarb(u32 p_port, unsigned char p_sel_type);
  690. static void FPT_scbusf(u32 p_port);
  691. static void FPT_scsel(u32 p_port);
  692. static void FPT_scasid(unsigned char p_card, u32 p_port);
  693. static unsigned char FPT_scxferc(u32 p_port, unsigned char p_data);
  694. static unsigned char FPT_scsendi(u32 p_port,
  695. unsigned char p_id_string[]);
  696. static unsigned char FPT_sciso(u32 p_port,
  697. unsigned char p_id_string[]);
  698. static void FPT_scwirod(u32 p_port, unsigned char p_data_bit);
  699. static void FPT_scwiros(u32 p_port, unsigned char p_data_bit);
  700. static unsigned char FPT_scvalq(unsigned char p_quintet);
  701. static unsigned char FPT_scsell(u32 p_port, unsigned char targ_id);
  702. static void FPT_scwtsel(u32 p_port);
  703. static void FPT_inisci(unsigned char p_card, u32 p_port,
  704. unsigned char p_our_id);
  705. static void FPT_scsavdi(unsigned char p_card, u32 p_port);
  706. static unsigned char FPT_scmachid(unsigned char p_card,
  707. unsigned char p_id_string[]);
  708. static void FPT_autoCmdCmplt(u32 p_port, unsigned char p_card);
  709. static void FPT_autoLoadDefaultMap(u32 p_port);
  710. static struct sccb_mgr_tar_info FPT_sccbMgrTbl[MAX_CARDS][MAX_SCSI_TAR] =
  711. { {{0}} };
  712. static struct sccb_card FPT_BL_Card[MAX_CARDS] = { {0} };
  713. static SCCBSCAM_INFO FPT_scamInfo[MAX_SCSI_TAR] = { {{0}} };
  714. static struct nvram_info FPT_nvRamInfo[MAX_MB_CARDS] = { {0} };
  715. static unsigned char FPT_mbCards = 0;
  716. static unsigned char FPT_scamHAString[] =
  717. { 0x63, 0x07, 'B', 'U', 'S', 'L', 'O', 'G', 'I', 'C',
  718. ' ', 'B', 'T', '-', '9', '3', '0',
  719. 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
  720. 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20
  721. };
  722. static unsigned short FPT_default_intena = 0;
  723. static void (*FPT_s_PhaseTbl[8]) (u32, unsigned char) = {
  724. 0};
  725. /*---------------------------------------------------------------------
  726. *
  727. * Function: FlashPoint_ProbeHostAdapter
  728. *
  729. * Description: Setup and/or Search for cards and return info to caller.
  730. *
  731. *---------------------------------------------------------------------*/
  732. static int FlashPoint_ProbeHostAdapter(struct sccb_mgr_info *pCardInfo)
  733. {
  734. static unsigned char first_time = 1;
  735. unsigned char i, j, id, ScamFlg;
  736. unsigned short temp, temp2, temp3, temp4, temp5, temp6;
  737. u32 ioport;
  738. struct nvram_info *pCurrNvRam;
  739. ioport = pCardInfo->si_baseaddr;
  740. if (RD_HARPOON(ioport + hp_vendor_id_0) != ORION_VEND_0)
  741. return (int)FAILURE;
  742. if ((RD_HARPOON(ioport + hp_vendor_id_1) != ORION_VEND_1))
  743. return (int)FAILURE;
  744. if ((RD_HARPOON(ioport + hp_device_id_0) != ORION_DEV_0))
  745. return (int)FAILURE;
  746. if ((RD_HARPOON(ioport + hp_device_id_1) != ORION_DEV_1))
  747. return (int)FAILURE;
  748. if (RD_HARPOON(ioport + hp_rev_num) != 0x0f) {
  749. /* For new Harpoon then check for sub_device ID LSB
  750. the bits(0-3) must be all ZERO for compatible with
  751. current version of SCCBMgr, else skip this Harpoon
  752. device. */
  753. if (RD_HARPOON(ioport + hp_sub_device_id_0) & 0x0f)
  754. return (int)FAILURE;
  755. }
  756. if (first_time) {
  757. FPT_SccbMgrTableInitAll();
  758. first_time = 0;
  759. FPT_mbCards = 0;
  760. }
  761. if (FPT_RdStack(ioport, 0) != 0x00) {
  762. if (FPT_ChkIfChipInitialized(ioport) == 0) {
  763. pCurrNvRam = NULL;
  764. WR_HARPOON(ioport + hp_semaphore, 0x00);
  765. FPT_XbowInit(ioport, 0); /*Must Init the SCSI before attempting */
  766. FPT_DiagEEPROM(ioport);
  767. } else {
  768. if (FPT_mbCards < MAX_MB_CARDS) {
  769. pCurrNvRam = &FPT_nvRamInfo[FPT_mbCards];
  770. FPT_mbCards++;
  771. pCurrNvRam->niBaseAddr = ioport;
  772. FPT_RNVRamData(pCurrNvRam);
  773. } else
  774. return (int)FAILURE;
  775. }
  776. } else
  777. pCurrNvRam = NULL;
  778. WR_HARPOON(ioport + hp_clkctrl_0, CLKCTRL_DEFAULT);
  779. WR_HARPOON(ioport + hp_sys_ctrl, 0x00);
  780. if (pCurrNvRam)
  781. pCardInfo->si_id = pCurrNvRam->niAdapId;
  782. else
  783. pCardInfo->si_id =
  784. (unsigned
  785. char)(FPT_utilEERead(ioport,
  786. (ADAPTER_SCSI_ID /
  787. 2)) & (unsigned char)0x0FF);
  788. pCardInfo->si_lun = 0x00;
  789. pCardInfo->si_fw_revision = ORION_FW_REV;
  790. temp2 = 0x0000;
  791. temp3 = 0x0000;
  792. temp4 = 0x0000;
  793. temp5 = 0x0000;
  794. temp6 = 0x0000;
  795. for (id = 0; id < (16 / 2); id++) {
  796. if (pCurrNvRam) {
  797. temp = (unsigned short)pCurrNvRam->niSyncTbl[id];
  798. temp = ((temp & 0x03) + ((temp << 4) & 0xc0)) +
  799. (((temp << 4) & 0x0300) + ((temp << 8) & 0xc000));
  800. } else
  801. temp =
  802. FPT_utilEERead(ioport,
  803. (unsigned short)((SYNC_RATE_TBL / 2)
  804. + id));
  805. for (i = 0; i < 2; temp >>= 8, i++) {
  806. temp2 >>= 1;
  807. temp3 >>= 1;
  808. temp4 >>= 1;
  809. temp5 >>= 1;
  810. temp6 >>= 1;
  811. switch (temp & 0x3) {
  812. case AUTO_RATE_20: /* Synchronous, 20 mega-transfers/second */
  813. temp6 |= 0x8000; /* Fall through */
  814. case AUTO_RATE_10: /* Synchronous, 10 mega-transfers/second */
  815. temp5 |= 0x8000; /* Fall through */
  816. case AUTO_RATE_05: /* Synchronous, 5 mega-transfers/second */
  817. temp2 |= 0x8000; /* Fall through */
  818. case AUTO_RATE_00: /* Asynchronous */
  819. break;
  820. }
  821. if (temp & DISC_ENABLE_BIT)
  822. temp3 |= 0x8000;
  823. if (temp & WIDE_NEGO_BIT)
  824. temp4 |= 0x8000;
  825. }
  826. }
  827. pCardInfo->si_per_targ_init_sync = temp2;
  828. pCardInfo->si_per_targ_no_disc = temp3;
  829. pCardInfo->si_per_targ_wide_nego = temp4;
  830. pCardInfo->si_per_targ_fast_nego = temp5;
  831. pCardInfo->si_per_targ_ultra_nego = temp6;
  832. if (pCurrNvRam)
  833. i = pCurrNvRam->niSysConf;
  834. else
  835. i = (unsigned
  836. char)(FPT_utilEERead(ioport, (SYSTEM_CONFIG / 2)));
  837. if (pCurrNvRam)
  838. ScamFlg = pCurrNvRam->niScamConf;
  839. else
  840. ScamFlg =
  841. (unsigned char)FPT_utilEERead(ioport, SCAM_CONFIG / 2);
  842. pCardInfo->si_flags = 0x0000;
  843. if (i & 0x01)
  844. pCardInfo->si_flags |= SCSI_PARITY_ENA;
  845. if (!(i & 0x02))
  846. pCardInfo->si_flags |= SOFT_RESET;
  847. if (i & 0x10)
  848. pCardInfo->si_flags |= EXTENDED_TRANSLATION;
  849. if (ScamFlg & SCAM_ENABLED)
  850. pCardInfo->si_flags |= FLAG_SCAM_ENABLED;
  851. if (ScamFlg & SCAM_LEVEL2)
  852. pCardInfo->si_flags |= FLAG_SCAM_LEVEL2;
  853. j = (RD_HARPOON(ioport + hp_bm_ctrl) & ~SCSI_TERM_ENA_L);
  854. if (i & 0x04) {
  855. j |= SCSI_TERM_ENA_L;
  856. }
  857. WR_HARPOON(ioport + hp_bm_ctrl, j);
  858. j = (RD_HARPOON(ioport + hp_ee_ctrl) & ~SCSI_TERM_ENA_H);
  859. if (i & 0x08) {
  860. j |= SCSI_TERM_ENA_H;
  861. }
  862. WR_HARPOON(ioport + hp_ee_ctrl, j);
  863. if (!(RD_HARPOON(ioport + hp_page_ctrl) & NARROW_SCSI_CARD))
  864. pCardInfo->si_flags |= SUPPORT_16TAR_32LUN;
  865. pCardInfo->si_card_family = HARPOON_FAMILY;
  866. pCardInfo->si_bustype = BUSTYPE_PCI;
  867. if (pCurrNvRam) {
  868. pCardInfo->si_card_model[0] = '9';
  869. switch (pCurrNvRam->niModel & 0x0f) {
  870. case MODEL_LT:
  871. pCardInfo->si_card_model[1] = '3';
  872. pCardInfo->si_card_model[2] = '0';
  873. break;
  874. case MODEL_LW:
  875. pCardInfo->si_card_model[1] = '5';
  876. pCardInfo->si_card_model[2] = '0';
  877. break;
  878. case MODEL_DL:
  879. pCardInfo->si_card_model[1] = '3';
  880. pCardInfo->si_card_model[2] = '2';
  881. break;
  882. case MODEL_DW:
  883. pCardInfo->si_card_model[1] = '5';
  884. pCardInfo->si_card_model[2] = '2';
  885. break;
  886. }
  887. } else {
  888. temp = FPT_utilEERead(ioport, (MODEL_NUMB_0 / 2));
  889. pCardInfo->si_card_model[0] = (unsigned char)(temp >> 8);
  890. temp = FPT_utilEERead(ioport, (MODEL_NUMB_2 / 2));
  891. pCardInfo->si_card_model[1] = (unsigned char)(temp & 0x00FF);
  892. pCardInfo->si_card_model[2] = (unsigned char)(temp >> 8);
  893. }
  894. if (pCardInfo->si_card_model[1] == '3') {
  895. if (RD_HARPOON(ioport + hp_ee_ctrl) & BIT(7))
  896. pCardInfo->si_flags |= LOW_BYTE_TERM;
  897. } else if (pCardInfo->si_card_model[2] == '0') {
  898. temp = RD_HARPOON(ioport + hp_xfer_pad);
  899. WR_HARPOON(ioport + hp_xfer_pad, (temp & ~BIT(4)));
  900. if (RD_HARPOON(ioport + hp_ee_ctrl) & BIT(7))
  901. pCardInfo->si_flags |= LOW_BYTE_TERM;
  902. WR_HARPOON(ioport + hp_xfer_pad, (temp | BIT(4)));
  903. if (RD_HARPOON(ioport + hp_ee_ctrl) & BIT(7))
  904. pCardInfo->si_flags |= HIGH_BYTE_TERM;
  905. WR_HARPOON(ioport + hp_xfer_pad, temp);
  906. } else {
  907. temp = RD_HARPOON(ioport + hp_ee_ctrl);
  908. temp2 = RD_HARPOON(ioport + hp_xfer_pad);
  909. WR_HARPOON(ioport + hp_ee_ctrl, (temp | SEE_CS));
  910. WR_HARPOON(ioport + hp_xfer_pad, (temp2 | BIT(4)));
  911. temp3 = 0;
  912. for (i = 0; i < 8; i++) {
  913. temp3 <<= 1;
  914. if (!(RD_HARPOON(ioport + hp_ee_ctrl) & BIT(7)))
  915. temp3 |= 1;
  916. WR_HARPOON(ioport + hp_xfer_pad, (temp2 & ~BIT(4)));
  917. WR_HARPOON(ioport + hp_xfer_pad, (temp2 | BIT(4)));
  918. }
  919. WR_HARPOON(ioport + hp_ee_ctrl, temp);
  920. WR_HARPOON(ioport + hp_xfer_pad, temp2);
  921. if (!(temp3 & BIT(7)))
  922. pCardInfo->si_flags |= LOW_BYTE_TERM;
  923. if (!(temp3 & BIT(6)))
  924. pCardInfo->si_flags |= HIGH_BYTE_TERM;
  925. }
  926. ARAM_ACCESS(ioport);
  927. for (i = 0; i < 4; i++) {
  928. pCardInfo->si_XlatInfo[i] =
  929. RD_HARPOON(ioport + hp_aramBase + BIOS_DATA_OFFSET + i);
  930. }
  931. /* return with -1 if no sort, else return with
  932. logical card number sorted by BIOS (zero-based) */
  933. pCardInfo->si_relative_cardnum =
  934. (unsigned
  935. char)(RD_HARPOON(ioport + hp_aramBase + BIOS_RELATIVE_CARD) - 1);
  936. SGRAM_ACCESS(ioport);
  937. FPT_s_PhaseTbl[0] = FPT_phaseDataOut;
  938. FPT_s_PhaseTbl[1] = FPT_phaseDataIn;
  939. FPT_s_PhaseTbl[2] = FPT_phaseIllegal;
  940. FPT_s_PhaseTbl[3] = FPT_phaseIllegal;
  941. FPT_s_PhaseTbl[4] = FPT_phaseCommand;
  942. FPT_s_PhaseTbl[5] = FPT_phaseStatus;
  943. FPT_s_PhaseTbl[6] = FPT_phaseMsgOut;
  944. FPT_s_PhaseTbl[7] = FPT_phaseMsgIn;
  945. pCardInfo->si_present = 0x01;
  946. return 0;
  947. }
  948. /*---------------------------------------------------------------------
  949. *
  950. * Function: FlashPoint_HardwareResetHostAdapter
  951. *
  952. * Description: Setup adapter for normal operation (hard reset).
  953. *
  954. *---------------------------------------------------------------------*/
  955. static void *FlashPoint_HardwareResetHostAdapter(struct sccb_mgr_info
  956. *pCardInfo)
  957. {
  958. struct sccb_card *CurrCard = NULL;
  959. struct nvram_info *pCurrNvRam;
  960. unsigned char i, j, thisCard, ScamFlg;
  961. unsigned short temp, sync_bit_map, id;
  962. u32 ioport;
  963. ioport = pCardInfo->si_baseaddr;
  964. for (thisCard = 0; thisCard <= MAX_CARDS; thisCard++) {
  965. if (thisCard == MAX_CARDS)
  966. return (void *)FAILURE;
  967. if (FPT_BL_Card[thisCard].ioPort == ioport) {
  968. CurrCard = &FPT_BL_Card[thisCard];
  969. FPT_SccbMgrTableInitCard(CurrCard, thisCard);
  970. break;
  971. }
  972. else if (FPT_BL_Card[thisCard].ioPort == 0x00) {
  973. FPT_BL_Card[thisCard].ioPort = ioport;
  974. CurrCard = &FPT_BL_Card[thisCard];
  975. if (FPT_mbCards)
  976. for (i = 0; i < FPT_mbCards; i++) {
  977. if (CurrCard->ioPort ==
  978. FPT_nvRamInfo[i].niBaseAddr)
  979. CurrCard->pNvRamInfo =
  980. &FPT_nvRamInfo[i];
  981. }
  982. FPT_SccbMgrTableInitCard(CurrCard, thisCard);
  983. CurrCard->cardIndex = thisCard;
  984. CurrCard->cardInfo = pCardInfo;
  985. break;
  986. }
  987. }
  988. pCurrNvRam = CurrCard->pNvRamInfo;
  989. if (pCurrNvRam) {
  990. ScamFlg = pCurrNvRam->niScamConf;
  991. } else {
  992. ScamFlg =
  993. (unsigned char)FPT_utilEERead(ioport, SCAM_CONFIG / 2);
  994. }
  995. FPT_BusMasterInit(ioport);
  996. FPT_XbowInit(ioport, ScamFlg);
  997. FPT_autoLoadDefaultMap(ioport);
  998. for (i = 0, id = 0x01; i != pCardInfo->si_id; i++, id <<= 1) {
  999. }
  1000. WR_HARPOON(ioport + hp_selfid_0, id);
  1001. WR_HARPOON(ioport + hp_selfid_1, 0x00);
  1002. WR_HARPOON(ioport + hp_arb_id, pCardInfo->si_id);
  1003. CurrCard->ourId = pCardInfo->si_id;
  1004. i = (unsigned char)pCardInfo->si_flags;
  1005. if (i & SCSI_PARITY_ENA)
  1006. WR_HARPOON(ioport + hp_portctrl_1, (HOST_MODE8 | CHK_SCSI_P));
  1007. j = (RD_HARPOON(ioport + hp_bm_ctrl) & ~SCSI_TERM_ENA_L);
  1008. if (i & LOW_BYTE_TERM)
  1009. j |= SCSI_TERM_ENA_L;
  1010. WR_HARPOON(ioport + hp_bm_ctrl, j);
  1011. j = (RD_HARPOON(ioport + hp_ee_ctrl) & ~SCSI_TERM_ENA_H);
  1012. if (i & HIGH_BYTE_TERM)
  1013. j |= SCSI_TERM_ENA_H;
  1014. WR_HARPOON(ioport + hp_ee_ctrl, j);
  1015. if (!(pCardInfo->si_flags & SOFT_RESET)) {
  1016. FPT_sresb(ioport, thisCard);
  1017. FPT_scini(thisCard, pCardInfo->si_id, 0);
  1018. }
  1019. if (pCardInfo->si_flags & POST_ALL_UNDERRRUNS)
  1020. CurrCard->globalFlags |= F_NO_FILTER;
  1021. if (pCurrNvRam) {
  1022. if (pCurrNvRam->niSysConf & 0x10)
  1023. CurrCard->globalFlags |= F_GREEN_PC;
  1024. } else {
  1025. if (FPT_utilEERead(ioport, (SYSTEM_CONFIG / 2)) & GREEN_PC_ENA)
  1026. CurrCard->globalFlags |= F_GREEN_PC;
  1027. }
  1028. /* Set global flag to indicate Re-Negotiation to be done on all
  1029. ckeck condition */
  1030. if (pCurrNvRam) {
  1031. if (pCurrNvRam->niScsiConf & 0x04)
  1032. CurrCard->globalFlags |= F_DO_RENEGO;
  1033. } else {
  1034. if (FPT_utilEERead(ioport, (SCSI_CONFIG / 2)) & RENEGO_ENA)
  1035. CurrCard->globalFlags |= F_DO_RENEGO;
  1036. }
  1037. if (pCurrNvRam) {
  1038. if (pCurrNvRam->niScsiConf & 0x08)
  1039. CurrCard->globalFlags |= F_CONLUN_IO;
  1040. } else {
  1041. if (FPT_utilEERead(ioport, (SCSI_CONFIG / 2)) & CONNIO_ENA)
  1042. CurrCard->globalFlags |= F_CONLUN_IO;
  1043. }
  1044. temp = pCardInfo->si_per_targ_no_disc;
  1045. for (i = 0, id = 1; i < MAX_SCSI_TAR; i++, id <<= 1) {
  1046. if (temp & id)
  1047. FPT_sccbMgrTbl[thisCard][i].TarStatus |= TAR_ALLOW_DISC;
  1048. }
  1049. sync_bit_map = 0x0001;
  1050. for (id = 0; id < (MAX_SCSI_TAR / 2); id++) {
  1051. if (pCurrNvRam) {
  1052. temp = (unsigned short)pCurrNvRam->niSyncTbl[id];
  1053. temp = ((temp & 0x03) + ((temp << 4) & 0xc0)) +
  1054. (((temp << 4) & 0x0300) + ((temp << 8) & 0xc000));
  1055. } else
  1056. temp =
  1057. FPT_utilEERead(ioport,
  1058. (unsigned short)((SYNC_RATE_TBL / 2)
  1059. + id));
  1060. for (i = 0; i < 2; temp >>= 8, i++) {
  1061. if (pCardInfo->si_per_targ_init_sync & sync_bit_map) {
  1062. FPT_sccbMgrTbl[thisCard][id * 2 +
  1063. i].TarEEValue =
  1064. (unsigned char)temp;
  1065. }
  1066. else {
  1067. FPT_sccbMgrTbl[thisCard][id * 2 +
  1068. i].TarStatus |=
  1069. SYNC_SUPPORTED;
  1070. FPT_sccbMgrTbl[thisCard][id * 2 +
  1071. i].TarEEValue =
  1072. (unsigned char)(temp & ~EE_SYNC_MASK);
  1073. }
  1074. /* if ((pCardInfo->si_per_targ_wide_nego & sync_bit_map) ||
  1075. (id*2+i >= 8)){
  1076. */
  1077. if (pCardInfo->si_per_targ_wide_nego & sync_bit_map) {
  1078. FPT_sccbMgrTbl[thisCard][id * 2 +
  1079. i].TarEEValue |=
  1080. EE_WIDE_SCSI;
  1081. }
  1082. else { /* NARROW SCSI */
  1083. FPT_sccbMgrTbl[thisCard][id * 2 +
  1084. i].TarStatus |=
  1085. WIDE_NEGOCIATED;
  1086. }
  1087. sync_bit_map <<= 1;
  1088. }
  1089. }
  1090. WR_HARPOON((ioport + hp_semaphore),
  1091. (unsigned char)(RD_HARPOON((ioport + hp_semaphore)) |
  1092. SCCB_MGR_PRESENT));
  1093. return (void *)CurrCard;
  1094. }
  1095. static void FlashPoint_ReleaseHostAdapter(void *pCurrCard)
  1096. {
  1097. unsigned char i;
  1098. u32 portBase;
  1099. u32 regOffset;
  1100. u32 scamData;
  1101. u32 *pScamTbl;
  1102. struct nvram_info *pCurrNvRam;
  1103. pCurrNvRam = ((struct sccb_card *)pCurrCard)->pNvRamInfo;
  1104. if (pCurrNvRam) {
  1105. FPT_WrStack(pCurrNvRam->niBaseAddr, 0, pCurrNvRam->niModel);
  1106. FPT_WrStack(pCurrNvRam->niBaseAddr, 1, pCurrNvRam->niSysConf);
  1107. FPT_WrStack(pCurrNvRam->niBaseAddr, 2, pCurrNvRam->niScsiConf);
  1108. FPT_WrStack(pCurrNvRam->niBaseAddr, 3, pCurrNvRam->niScamConf);
  1109. FPT_WrStack(pCurrNvRam->niBaseAddr, 4, pCurrNvRam->niAdapId);
  1110. for (i = 0; i < MAX_SCSI_TAR / 2; i++)
  1111. FPT_WrStack(pCurrNvRam->niBaseAddr,
  1112. (unsigned char)(i + 5),
  1113. pCurrNvRam->niSyncTbl[i]);
  1114. portBase = pCurrNvRam->niBaseAddr;
  1115. for (i = 0; i < MAX_SCSI_TAR; i++) {
  1116. regOffset = hp_aramBase + 64 + i * 4;
  1117. pScamTbl = (u32 *)&pCurrNvRam->niScamTbl[i];
  1118. scamData = *pScamTbl;
  1119. WR_HARP32(portBase, regOffset, scamData);
  1120. }
  1121. } else {
  1122. FPT_WrStack(((struct sccb_card *)pCurrCard)->ioPort, 0, 0);
  1123. }
  1124. }
  1125. static void FPT_RNVRamData(struct nvram_info *pNvRamInfo)
  1126. {
  1127. unsigned char i;
  1128. u32 portBase;
  1129. u32 regOffset;
  1130. u32 scamData;
  1131. u32 *pScamTbl;
  1132. pNvRamInfo->niModel = FPT_RdStack(pNvRamInfo->niBaseAddr, 0);
  1133. pNvRamInfo->niSysConf = FPT_RdStack(pNvRamInfo->niBaseAddr, 1);
  1134. pNvRamInfo->niScsiConf = FPT_RdStack(pNvRamInfo->niBaseAddr, 2);
  1135. pNvRamInfo->niScamConf = FPT_RdStack(pNvRamInfo->niBaseAddr, 3);
  1136. pNvRamInfo->niAdapId = FPT_RdStack(pNvRamInfo->niBaseAddr, 4);
  1137. for (i = 0; i < MAX_SCSI_TAR / 2; i++)
  1138. pNvRamInfo->niSyncTbl[i] =
  1139. FPT_RdStack(pNvRamInfo->niBaseAddr, (unsigned char)(i + 5));
  1140. portBase = pNvRamInfo->niBaseAddr;
  1141. for (i = 0; i < MAX_SCSI_TAR; i++) {
  1142. regOffset = hp_aramBase + 64 + i * 4;
  1143. RD_HARP32(portBase, regOffset, scamData);
  1144. pScamTbl = (u32 *)&pNvRamInfo->niScamTbl[i];
  1145. *pScamTbl = scamData;
  1146. }
  1147. }
  1148. static unsigned char FPT_RdStack(u32 portBase, unsigned char index)
  1149. {
  1150. WR_HARPOON(portBase + hp_stack_addr, index);
  1151. return RD_HARPOON(portBase + hp_stack_data);
  1152. }
  1153. static void FPT_WrStack(u32 portBase, unsigned char index, unsigned char data)
  1154. {
  1155. WR_HARPOON(portBase + hp_stack_addr, index);
  1156. WR_HARPOON(portBase + hp_stack_data, data);
  1157. }
  1158. static unsigned char FPT_ChkIfChipInitialized(u32 ioPort)
  1159. {
  1160. if ((RD_HARPOON(ioPort + hp_arb_id) & 0x0f) != FPT_RdStack(ioPort, 4))
  1161. return 0;
  1162. if ((RD_HARPOON(ioPort + hp_clkctrl_0) & CLKCTRL_DEFAULT)
  1163. != CLKCTRL_DEFAULT)
  1164. return 0;
  1165. if ((RD_HARPOON(ioPort + hp_seltimeout) == TO_250ms) ||
  1166. (RD_HARPOON(ioPort + hp_seltimeout) == TO_290ms))
  1167. return 1;
  1168. return 0;
  1169. }
  1170. /*---------------------------------------------------------------------
  1171. *
  1172. * Function: FlashPoint_StartCCB
  1173. *
  1174. * Description: Start a command pointed to by p_Sccb. When the
  1175. * command is completed it will be returned via the
  1176. * callback function.
  1177. *
  1178. *---------------------------------------------------------------------*/
  1179. static void FlashPoint_StartCCB(void *curr_card, struct sccb *p_Sccb)
  1180. {
  1181. u32 ioport;
  1182. unsigned char thisCard, lun;
  1183. struct sccb *pSaveSccb;
  1184. CALL_BK_FN callback;
  1185. struct sccb_card *pCurrCard = curr_card;
  1186. thisCard = pCurrCard->cardIndex;
  1187. ioport = pCurrCard->ioPort;
  1188. if ((p_Sccb->TargID >= MAX_SCSI_TAR) || (p_Sccb->Lun >= MAX_LUN)) {
  1189. p_Sccb->HostStatus = SCCB_COMPLETE;
  1190. p_Sccb->SccbStatus = SCCB_ERROR;
  1191. callback = (CALL_BK_FN) p_Sccb->SccbCallback;
  1192. if (callback)
  1193. callback(p_Sccb);
  1194. return;
  1195. }
  1196. FPT_sinits(p_Sccb, thisCard);
  1197. if (!pCurrCard->cmdCounter) {
  1198. WR_HARPOON(ioport + hp_semaphore,
  1199. (RD_HARPOON(ioport + hp_semaphore)
  1200. | SCCB_MGR_ACTIVE));
  1201. if (pCurrCard->globalFlags & F_GREEN_PC) {
  1202. WR_HARPOON(ioport + hp_clkctrl_0, CLKCTRL_DEFAULT);
  1203. WR_HARPOON(ioport + hp_sys_ctrl, 0x00);
  1204. }
  1205. }
  1206. pCurrCard->cmdCounter++;
  1207. if (RD_HARPOON(ioport + hp_semaphore) & BIOS_IN_USE) {
  1208. WR_HARPOON(ioport + hp_semaphore,
  1209. (RD_HARPOON(ioport + hp_semaphore)
  1210. | TICKLE_ME));
  1211. if (p_Sccb->OperationCode == RESET_COMMAND) {
  1212. pSaveSccb =
  1213. pCurrCard->currentSCCB;
  1214. pCurrCard->currentSCCB = p_Sccb;
  1215. FPT_queueSelectFail(&FPT_BL_Card[thisCard], thisCard);
  1216. pCurrCard->currentSCCB =
  1217. pSaveSccb;
  1218. } else {
  1219. FPT_queueAddSccb(p_Sccb, thisCard);
  1220. }
  1221. }
  1222. else if ((RD_HARPOON(ioport + hp_page_ctrl) & G_INT_DISABLE)) {
  1223. if (p_Sccb->OperationCode == RESET_COMMAND) {
  1224. pSaveSccb =
  1225. pCurrCard->currentSCCB;
  1226. pCurrCard->currentSCCB = p_Sccb;
  1227. FPT_queueSelectFail(&FPT_BL_Card[thisCard], thisCard);
  1228. pCurrCard->currentSCCB =
  1229. pSaveSccb;
  1230. } else {
  1231. FPT_queueAddSccb(p_Sccb, thisCard);
  1232. }
  1233. }
  1234. else {
  1235. MDISABLE_INT(ioport);
  1236. if ((pCurrCard->globalFlags & F_CONLUN_IO) &&
  1237. ((FPT_sccbMgrTbl[thisCard][p_Sccb->TargID].
  1238. TarStatus & TAR_TAG_Q_MASK) != TAG_Q_TRYING))
  1239. lun = p_Sccb->Lun;
  1240. else
  1241. lun = 0;
  1242. if ((pCurrCard->currentSCCB == NULL) &&
  1243. (FPT_sccbMgrTbl[thisCard][p_Sccb->TargID].TarSelQ_Cnt == 0)
  1244. && (FPT_sccbMgrTbl[thisCard][p_Sccb->TargID].TarLUNBusy[lun]
  1245. == 0)) {
  1246. pCurrCard->currentSCCB = p_Sccb;
  1247. FPT_ssel(p_Sccb->SccbIOPort, thisCard);
  1248. }
  1249. else {
  1250. if (p_Sccb->OperationCode == RESET_COMMAND) {
  1251. pSaveSccb = pCurrCard->currentSCCB;
  1252. pCurrCard->currentSCCB = p_Sccb;
  1253. FPT_queueSelectFail(&FPT_BL_Card[thisCard],
  1254. thisCard);
  1255. pCurrCard->currentSCCB = pSaveSccb;
  1256. } else {
  1257. FPT_queueAddSccb(p_Sccb, thisCard);
  1258. }
  1259. }
  1260. MENABLE_INT(ioport);
  1261. }
  1262. }
  1263. /*---------------------------------------------------------------------
  1264. *
  1265. * Function: FlashPoint_AbortCCB
  1266. *
  1267. * Description: Abort the command pointed to by p_Sccb. When the
  1268. * command is completed it will be returned via the
  1269. * callback function.
  1270. *
  1271. *---------------------------------------------------------------------*/
  1272. static int FlashPoint_AbortCCB(void *pCurrCard, struct sccb *p_Sccb)
  1273. {
  1274. u32 ioport;
  1275. unsigned char thisCard;
  1276. CALL_BK_FN callback;
  1277. unsigned char TID;
  1278. struct sccb *pSaveSCCB;
  1279. struct sccb_mgr_tar_info *currTar_Info;
  1280. ioport = ((struct sccb_card *)pCurrCard)->ioPort;
  1281. thisCard = ((struct sccb_card *)pCurrCard)->cardIndex;
  1282. if (!(RD_HARPOON(ioport + hp_page_ctrl) & G_INT_DISABLE)) {
  1283. if (FPT_queueFindSccb(p_Sccb, thisCard)) {
  1284. ((struct sccb_card *)pCurrCard)->cmdCounter--;
  1285. if (!((struct sccb_card *)pCurrCard)->cmdCounter)
  1286. WR_HARPOON(ioport + hp_semaphore,
  1287. (RD_HARPOON(ioport + hp_semaphore)
  1288. & (unsigned
  1289. char)(~(SCCB_MGR_ACTIVE |
  1290. TICKLE_ME))));
  1291. p_Sccb->SccbStatus = SCCB_ABORT;
  1292. callback = p_Sccb->SccbCallback;
  1293. callback(p_Sccb);
  1294. return 0;
  1295. }
  1296. else {
  1297. if (((struct sccb_card *)pCurrCard)->currentSCCB ==
  1298. p_Sccb) {
  1299. p_Sccb->SccbStatus = SCCB_ABORT;
  1300. return 0;
  1301. }
  1302. else {
  1303. TID = p_Sccb->TargID;
  1304. if (p_Sccb->Sccb_tag) {
  1305. MDISABLE_INT(ioport);
  1306. if (((struct sccb_card *)pCurrCard)->
  1307. discQ_Tbl[p_Sccb->Sccb_tag] ==
  1308. p_Sccb) {
  1309. p_Sccb->SccbStatus = SCCB_ABORT;
  1310. p_Sccb->Sccb_scsistat =
  1311. ABORT_ST;
  1312. p_Sccb->Sccb_scsimsg =
  1313. SMABORT_TAG;
  1314. if (((struct sccb_card *)
  1315. pCurrCard)->currentSCCB ==
  1316. NULL) {
  1317. ((struct sccb_card *)
  1318. pCurrCard)->
  1319. currentSCCB = p_Sccb;
  1320. FPT_ssel(ioport,
  1321. thisCard);
  1322. } else {
  1323. pSaveSCCB =
  1324. ((struct sccb_card
  1325. *)pCurrCard)->
  1326. currentSCCB;
  1327. ((struct sccb_card *)
  1328. pCurrCard)->
  1329. currentSCCB = p_Sccb;
  1330. FPT_queueSelectFail((struct sccb_card *)pCurrCard, thisCard);
  1331. ((struct sccb_card *)
  1332. pCurrCard)->
  1333. currentSCCB = pSaveSCCB;
  1334. }
  1335. }
  1336. MENABLE_INT(ioport);
  1337. return 0;
  1338. } else {
  1339. currTar_Info =
  1340. &FPT_sccbMgrTbl[thisCard][p_Sccb->
  1341. TargID];
  1342. if (FPT_BL_Card[thisCard].
  1343. discQ_Tbl[currTar_Info->
  1344. LunDiscQ_Idx[p_Sccb->Lun]]
  1345. == p_Sccb) {
  1346. p_Sccb->SccbStatus = SCCB_ABORT;
  1347. return 0;
  1348. }
  1349. }
  1350. }
  1351. }
  1352. }
  1353. return -1;
  1354. }
  1355. /*---------------------------------------------------------------------
  1356. *
  1357. * Function: FlashPoint_InterruptPending
  1358. *
  1359. * Description: Do a quick check to determine if there is a pending
  1360. * interrupt for this card and disable the IRQ Pin if so.
  1361. *
  1362. *---------------------------------------------------------------------*/
  1363. static unsigned char FlashPoint_InterruptPending(void *pCurrCard)
  1364. {
  1365. u32 ioport;
  1366. ioport = ((struct sccb_card *)pCurrCard)->ioPort;
  1367. if (RD_HARPOON(ioport + hp_int_status) & INT_ASSERTED) {
  1368. return 1;
  1369. }
  1370. else
  1371. return 0;
  1372. }
  1373. /*---------------------------------------------------------------------
  1374. *
  1375. * Function: FlashPoint_HandleInterrupt
  1376. *
  1377. * Description: This is our entry point when an interrupt is generated
  1378. * by the card and the upper level driver passes it on to
  1379. * us.
  1380. *
  1381. *---------------------------------------------------------------------*/
  1382. static int FlashPoint_HandleInterrupt(void *pcard)
  1383. {
  1384. struct sccb *currSCCB;
  1385. unsigned char thisCard, result, bm_status, bm_int_st;
  1386. unsigned short hp_int;
  1387. unsigned char i, target;
  1388. struct sccb_card *pCurrCard = pcard;
  1389. u32 ioport;
  1390. thisCard = pCurrCard->cardIndex;
  1391. ioport = pCurrCard->ioPort;
  1392. MDISABLE_INT(ioport);
  1393. if ((bm_int_st = RD_HARPOON(ioport + hp_int_status)) & EXT_STATUS_ON)
  1394. bm_status = RD_HARPOON(ioport + hp_ext_status) &
  1395. (unsigned char)BAD_EXT_STATUS;
  1396. else
  1397. bm_status = 0;
  1398. WR_HARPOON(ioport + hp_int_mask, (INT_CMD_COMPL | SCSI_INTERRUPT));
  1399. while ((hp_int = RDW_HARPOON((ioport + hp_intstat)) &
  1400. FPT_default_intena) | bm_status) {
  1401. currSCCB = pCurrCard->currentSCCB;
  1402. if (hp_int & (FIFO | TIMEOUT | RESET | SCAM_SEL) || bm_status) {
  1403. result =
  1404. FPT_SccbMgr_bad_isr(ioport, thisCard, pCurrCard,
  1405. hp_int);
  1406. WRW_HARPOON((ioport + hp_intstat),
  1407. (FIFO | TIMEOUT | RESET | SCAM_SEL));
  1408. bm_status = 0;
  1409. if (result) {
  1410. MENABLE_INT(ioport);
  1411. return result;
  1412. }
  1413. }
  1414. else if (hp_int & ICMD_COMP) {
  1415. if (!(hp_int & BUS_FREE)) {
  1416. /* Wait for the BusFree before starting a new command. We
  1417. must also check for being reselected since the BusFree
  1418. may not show up if another device reselects us in 1.5us or
  1419. less. SRR Wednesday, 3/8/1995.
  1420. */
  1421. while (!
  1422. (RDW_HARPOON((ioport + hp_intstat)) &
  1423. (BUS_FREE | RSEL))) ;
  1424. }
  1425. if (pCurrCard->globalFlags & F_HOST_XFER_ACT)
  1426. FPT_phaseChkFifo(ioport, thisCard);
  1427. /* WRW_HARPOON((ioport+hp_intstat),
  1428. (BUS_FREE | ICMD_COMP | ITAR_DISC | XFER_CNT_0));
  1429. */
  1430. WRW_HARPOON((ioport + hp_intstat), CLR_ALL_INT_1);
  1431. FPT_autoCmdCmplt(ioport, thisCard);
  1432. }
  1433. else if (hp_int & ITAR_DISC) {
  1434. if (pCurrCard->globalFlags & F_HOST_XFER_ACT)
  1435. FPT_phaseChkFifo(ioport, thisCard);
  1436. if (RD_HARPOON(ioport + hp_gp_reg_1) ==
  1437. SMSAVE_DATA_PTR) {
  1438. WR_HARPOON(ioport + hp_gp_reg_1, 0x00);
  1439. currSCCB->Sccb_XferState |= F_NO_DATA_YET;
  1440. currSCCB->Sccb_savedATC = currSCCB->Sccb_ATC;
  1441. }
  1442. currSCCB->Sccb_scsistat = DISCONNECT_ST;
  1443. FPT_queueDisconnect(currSCCB, thisCard);
  1444. /* Wait for the BusFree before starting a new command. We
  1445. must also check for being reselected since the BusFree
  1446. may not show up if another device reselects us in 1.5us or
  1447. less. SRR Wednesday, 3/8/1995.
  1448. */
  1449. while (!
  1450. (RDW_HARPOON((ioport + hp_intstat)) &
  1451. (BUS_FREE | RSEL))
  1452. && !((RDW_HARPOON((ioport + hp_intstat)) & PHASE)
  1453. && RD_HARPOON((ioport + hp_scsisig)) ==
  1454. (SCSI_BSY | SCSI_REQ | SCSI_CD | SCSI_MSG |
  1455. SCSI_IOBIT))) ;
  1456. /*
  1457. The additional loop exit condition above detects a timing problem
  1458. with the revision D/E harpoon chips. The caller should reset the
  1459. host adapter to recover when 0xFE is returned.
  1460. */
  1461. if (!
  1462. (RDW_HARPOON((ioport + hp_intstat)) &
  1463. (BUS_FREE | RSEL))) {
  1464. MENABLE_INT(ioport);
  1465. return 0xFE;
  1466. }
  1467. WRW_HARPOON((ioport + hp_intstat),
  1468. (BUS_FREE | ITAR_DISC));
  1469. pCurrCard->globalFlags |= F_NEW_SCCB_CMD;
  1470. }
  1471. else if (hp_int & RSEL) {
  1472. WRW_HARPOON((ioport + hp_intstat),
  1473. (PROG_HLT | RSEL | PHASE | BUS_FREE));
  1474. if (RDW_HARPOON((ioport + hp_intstat)) & ITAR_DISC) {
  1475. if (pCurrCard->globalFlags & F_HOST_XFER_ACT)
  1476. FPT_phaseChkFifo(ioport, thisCard);
  1477. if (RD_HARPOON(ioport + hp_gp_reg_1) ==
  1478. SMSAVE_DATA_PTR) {
  1479. WR_HARPOON(ioport + hp_gp_reg_1, 0x00);
  1480. currSCCB->Sccb_XferState |=
  1481. F_NO_DATA_YET;
  1482. currSCCB->Sccb_savedATC =
  1483. currSCCB->Sccb_ATC;
  1484. }
  1485. WRW_HARPOON((ioport + hp_intstat),
  1486. (BUS_FREE | ITAR_DISC));
  1487. currSCCB->Sccb_scsistat = DISCONNECT_ST;
  1488. FPT_queueDisconnect(currSCCB, thisCard);
  1489. }
  1490. FPT_sres(ioport, thisCard, pCurrCard);
  1491. FPT_phaseDecode(ioport, thisCard);
  1492. }
  1493. else if ((hp_int & IDO_STRT) && (!(hp_int & BUS_FREE))) {
  1494. WRW_HARPOON((ioport + hp_intstat),
  1495. (IDO_STRT | XFER_CNT_0));
  1496. FPT_phaseDecode(ioport, thisCard);
  1497. }
  1498. else if ((hp_int & IUNKWN) || (hp_int & PROG_HLT)) {
  1499. WRW_HARPOON((ioport + hp_intstat),
  1500. (PHASE | IUNKWN | PROG_HLT));
  1501. if ((RD_HARPOON(ioport + hp_prgmcnt_0) & (unsigned char)
  1502. 0x3f) < (unsigned char)SELCHK) {
  1503. FPT_phaseDecode(ioport, thisCard);
  1504. } else {
  1505. /* Harpoon problem some SCSI target device respond to selection
  1506. with short BUSY pulse (<400ns) this will make the Harpoon is not able
  1507. to latch the correct Target ID into reg. x53.
  1508. The work around require to correct this reg. But when write to this
  1509. reg. (0x53) also increment the FIFO write addr reg (0x6f), thus we
  1510. need to read this reg first then restore it later. After update to 0x53 */
  1511. i = (unsigned
  1512. char)(RD_HARPOON(ioport + hp_fifowrite));
  1513. target =
  1514. (unsigned
  1515. char)(RD_HARPOON(ioport + hp_gp_reg_3));
  1516. WR_HARPOON(ioport + hp_xfer_pad,
  1517. (unsigned char)ID_UNLOCK);
  1518. WR_HARPOON(ioport + hp_select_id,
  1519. (unsigned char)(target | target <<
  1520. 4));
  1521. WR_HARPOON(ioport + hp_xfer_pad,
  1522. (unsigned char)0x00);
  1523. WR_HARPOON(ioport + hp_fifowrite, i);
  1524. WR_HARPOON(ioport + hp_autostart_3,
  1525. (AUTO_IMMED + TAG_STRT));
  1526. }
  1527. }
  1528. else if (hp_int & XFER_CNT_0) {
  1529. WRW_HARPOON((ioport + hp_intstat), XFER_CNT_0);
  1530. FPT_schkdd(ioport, thisCard);
  1531. }
  1532. else if (hp_int & BUS_FREE) {
  1533. WRW_HARPOON((ioport + hp_intstat), BUS_FREE);
  1534. if (pCurrCard->globalFlags & F_HOST_XFER_ACT) {
  1535. FPT_hostDataXferAbort(ioport, thisCard,
  1536. currSCCB);
  1537. }
  1538. FPT_phaseBusFree(ioport, thisCard);
  1539. }
  1540. else if (hp_int & ITICKLE) {
  1541. WRW_HARPOON((ioport + hp_intstat), ITICKLE);
  1542. pCurrCard->globalFlags |= F_NEW_SCCB_CMD;
  1543. }
  1544. if (((struct sccb_card *)pCurrCard)->
  1545. globalFlags & F_NEW_SCCB_CMD) {
  1546. pCurrCard->globalFlags &= ~F_NEW_SCCB_CMD;
  1547. if (pCurrCard->currentSCCB == NULL)
  1548. FPT_queueSearchSelect(pCurrCard, thisCard);
  1549. if (pCurrCard->currentSCCB != NULL) {
  1550. pCurrCard->globalFlags &= ~F_NEW_SCCB_CMD;
  1551. FPT_ssel(ioport, thisCard);
  1552. }
  1553. break;
  1554. }
  1555. } /*end while */
  1556. MENABLE_INT(ioport);
  1557. return 0;
  1558. }
  1559. /*---------------------------------------------------------------------
  1560. *
  1561. * Function: Sccb_bad_isr
  1562. *
  1563. * Description: Some type of interrupt has occurred which is slightly
  1564. * out of the ordinary. We will now decode it fully, in
  1565. * this routine. This is broken up in an attempt to save
  1566. * processing time.
  1567. *
  1568. *---------------------------------------------------------------------*/
  1569. static unsigned char FPT_SccbMgr_bad_isr(u32 p_port, unsigned char p_card,
  1570. struct sccb_card *pCurrCard,
  1571. unsigned short p_int)
  1572. {
  1573. unsigned char temp, ScamFlg;
  1574. struct sccb_mgr_tar_info *currTar_Info;
  1575. struct nvram_info *pCurrNvRam;
  1576. if (RD_HARPOON(p_port + hp_ext_status) &
  1577. (BM_FORCE_OFF | PCI_DEV_TMOUT | BM_PARITY_ERR | PIO_OVERRUN)) {
  1578. if (pCurrCard->globalFlags & F_HOST_XFER_ACT) {
  1579. FPT_hostDataXferAbort(p_port, p_card,
  1580. pCurrCard->currentSCCB);
  1581. }
  1582. if (RD_HARPOON(p_port + hp_pci_stat_cfg) & REC_MASTER_ABORT)
  1583. {
  1584. WR_HARPOON(p_port + hp_pci_stat_cfg,
  1585. (RD_HARPOON(p_port + hp_pci_stat_cfg) &
  1586. ~REC_MASTER_ABORT));
  1587. WR_HARPOON(p_port + hp_host_blk_cnt, 0x00);
  1588. }
  1589. if (pCurrCard->currentSCCB != NULL) {
  1590. if (!pCurrCard->currentSCCB->HostStatus)
  1591. pCurrCard->currentSCCB->HostStatus =
  1592. SCCB_BM_ERR;
  1593. FPT_sxfrp(p_port, p_card);
  1594. temp = (unsigned char)(RD_HARPOON(p_port + hp_ee_ctrl) &
  1595. (EXT_ARB_ACK | SCSI_TERM_ENA_H));
  1596. WR_HARPOON(p_port + hp_ee_ctrl,
  1597. ((unsigned char)temp | SEE_MS | SEE_CS));
  1598. WR_HARPOON(p_port + hp_ee_ctrl, temp);
  1599. if (!
  1600. (RDW_HARPOON((p_port + hp_intstat)) &
  1601. (BUS_FREE | RESET))) {
  1602. FPT_phaseDecode(p_port, p_card);
  1603. }
  1604. }
  1605. }
  1606. else if (p_int & RESET) {
  1607. WR_HARPOON(p_port + hp_clkctrl_0, CLKCTRL_DEFAULT);
  1608. WR_HARPOON(p_port + hp_sys_ctrl, 0x00);
  1609. if (pCurrCard->currentSCCB != NULL) {
  1610. if (pCurrCard->globalFlags & F_HOST_XFER_ACT)
  1611. FPT_hostDataXferAbort(p_port, p_card,
  1612. pCurrCard->currentSCCB);
  1613. }
  1614. DISABLE_AUTO(p_port);
  1615. FPT_sresb(p_port, p_card);
  1616. while (RD_HARPOON(p_port + hp_scsictrl_0) & SCSI_RST) {
  1617. }
  1618. pCurrNvRam = pCurrCard->pNvRamInfo;
  1619. if (pCurrNvRam) {
  1620. ScamFlg = pCurrNvRam->niScamConf;
  1621. } else {
  1622. ScamFlg =
  1623. (unsigned char)FPT_utilEERead(p_port,
  1624. SCAM_CONFIG / 2);
  1625. }
  1626. FPT_XbowInit(p_port, ScamFlg);
  1627. FPT_scini(p_card, pCurrCard->ourId, 0);
  1628. return 0xFF;
  1629. }
  1630. else if (p_int & FIFO) {
  1631. WRW_HARPOON((p_port + hp_intstat), FIFO);
  1632. if (pCurrCard->currentSCCB != NULL)
  1633. FPT_sxfrp(p_port, p_card);
  1634. }
  1635. else if (p_int & TIMEOUT) {
  1636. DISABLE_AUTO(p_port);
  1637. WRW_HARPOON((p_port + hp_intstat),
  1638. (PROG_HLT | TIMEOUT | SEL | BUS_FREE | PHASE |
  1639. IUNKWN));
  1640. pCurrCard->currentSCCB->HostStatus = SCCB_SELECTION_TIMEOUT;
  1641. currTar_Info =
  1642. &FPT_sccbMgrTbl[p_card][pCurrCard->currentSCCB->TargID];
  1643. if ((pCurrCard->globalFlags & F_CONLUN_IO)
  1644. && ((currTar_Info->TarStatus & TAR_TAG_Q_MASK) !=
  1645. TAG_Q_TRYING))
  1646. currTar_Info->TarLUNBusy[pCurrCard->currentSCCB->Lun] =
  1647. 0;
  1648. else
  1649. currTar_Info->TarLUNBusy[0] = 0;
  1650. if (currTar_Info->TarEEValue & EE_SYNC_MASK) {
  1651. currTar_Info->TarSyncCtrl = 0;
  1652. currTar_Info->TarStatus &= ~TAR_SYNC_MASK;
  1653. }
  1654. if (currTar_Info->TarEEValue & EE_WIDE_SCSI) {
  1655. currTar_Info->TarStatus &= ~TAR_WIDE_MASK;
  1656. }
  1657. FPT_sssyncv(p_port, pCurrCard->currentSCCB->TargID, NARROW_SCSI,
  1658. currTar_Info);
  1659. FPT_queueCmdComplete(pCurrCard, pCurrCard->currentSCCB, p_card);
  1660. }
  1661. else if (p_int & SCAM_SEL) {
  1662. FPT_scarb(p_port, LEVEL2_TAR);
  1663. FPT_scsel(p_port);
  1664. FPT_scasid(p_card, p_port);
  1665. FPT_scbusf(p_port);
  1666. WRW_HARPOON((p_port + hp_intstat), SCAM_SEL);
  1667. }
  1668. return 0x00;
  1669. }
  1670. /*---------------------------------------------------------------------
  1671. *
  1672. * Function: SccbMgrTableInit
  1673. *
  1674. * Description: Initialize all Sccb manager data structures.
  1675. *
  1676. *---------------------------------------------------------------------*/
  1677. static void FPT_SccbMgrTableInitAll(void)
  1678. {
  1679. unsigned char thisCard;
  1680. for (thisCard = 0; thisCard < MAX_CARDS; thisCard++) {
  1681. FPT_SccbMgrTableInitCard(&FPT_BL_Card[thisCard], thisCard);
  1682. FPT_BL_Card[thisCard].ioPort = 0x00;
  1683. FPT_BL_Card[thisCard].cardInfo = NULL;
  1684. FPT_BL_Card[thisCard].cardIndex = 0xFF;
  1685. FPT_BL_Card[thisCard].ourId = 0x00;
  1686. FPT_BL_Card[thisCard].pNvRamInfo = NULL;
  1687. }
  1688. }
  1689. /*---------------------------------------------------------------------
  1690. *
  1691. * Function: SccbMgrTableInit
  1692. *
  1693. * Description: Initialize all Sccb manager data structures.
  1694. *
  1695. *---------------------------------------------------------------------*/
  1696. static void FPT_SccbMgrTableInitCard(struct sccb_card *pCurrCard,
  1697. unsigned char p_card)
  1698. {
  1699. unsigned char scsiID, qtag;
  1700. for (qtag = 0; qtag < QUEUE_DEPTH; qtag++) {
  1701. FPT_BL_Card[p_card].discQ_Tbl[qtag] = NULL;
  1702. }
  1703. for (scsiID = 0; scsiID < MAX_SCSI_TAR; scsiID++) {
  1704. FPT_sccbMgrTbl[p_card][scsiID].TarStatus = 0;
  1705. FPT_sccbMgrTbl[p_card][scsiID].TarEEValue = 0;
  1706. FPT_SccbMgrTableInitTarget(p_card, scsiID);
  1707. }
  1708. pCurrCard->scanIndex = 0x00;
  1709. pCurrCard->currentSCCB = NULL;
  1710. pCurrCard->globalFlags = 0x00;
  1711. pCurrCard->cmdCounter = 0x00;
  1712. pCurrCard->tagQ_Lst = 0x01;
  1713. pCurrCard->discQCount = 0;
  1714. }
  1715. /*---------------------------------------------------------------------
  1716. *
  1717. * Function: SccbMgrTableInit
  1718. *
  1719. * Description: Initialize all Sccb manager data structures.
  1720. *
  1721. *---------------------------------------------------------------------*/
  1722. static void FPT_SccbMgrTableInitTarget(unsigned char p_card,
  1723. unsigned char target)
  1724. {
  1725. unsigned char lun, qtag;
  1726. struct sccb_mgr_tar_info *currTar_Info;
  1727. currTar_Info = &FPT_sccbMgrTbl[p_card][target];
  1728. currTar_Info->TarSelQ_Cnt = 0;
  1729. currTar_Info->TarSyncCtrl = 0;
  1730. currTar_Info->TarSelQ_Head = NULL;
  1731. currTar_Info->TarSelQ_Tail = NULL;
  1732. currTar_Info->TarTagQ_Cnt = 0;
  1733. currTar_Info->TarLUN_CA = 0;
  1734. for (lun = 0; lun < MAX_LUN; lun++) {
  1735. currTar_Info->TarLUNBusy[lun] = 0;
  1736. currTar_Info->LunDiscQ_Idx[lun] = 0;
  1737. }
  1738. for (qtag = 0; qtag < QUEUE_DEPTH; qtag++) {
  1739. if (FPT_BL_Card[p_card].discQ_Tbl[qtag] != NULL) {
  1740. if (FPT_BL_Card[p_card].discQ_Tbl[qtag]->TargID ==
  1741. target) {
  1742. FPT_BL_Card[p_card].discQ_Tbl[qtag] = NULL;
  1743. FPT_BL_Card[p_card].discQCount--;
  1744. }
  1745. }
  1746. }
  1747. }
  1748. /*---------------------------------------------------------------------
  1749. *
  1750. * Function: sfetm
  1751. *
  1752. * Description: Read in a message byte from the SCSI bus, and check
  1753. * for a parity error.
  1754. *
  1755. *---------------------------------------------------------------------*/
  1756. static unsigned char FPT_sfm(u32 port, struct sccb *pCurrSCCB)
  1757. {
  1758. unsigned char message;
  1759. unsigned short TimeOutLoop;
  1760. TimeOutLoop = 0;
  1761. while ((!(RD_HARPOON(port + hp_scsisig) & SCSI_REQ)) &&
  1762. (TimeOutLoop++ < 20000)) {
  1763. }
  1764. WR_HARPOON(port + hp_portctrl_0, SCSI_PORT);
  1765. message = RD_HARPOON(port + hp_scsidata_0);
  1766. WR_HARPOON(port + hp_scsisig, SCSI_ACK + S_MSGI_PH);
  1767. if (TimeOutLoop > 20000)
  1768. message = 0x00; /* force message byte = 0 if Time Out on Req */
  1769. if ((RDW_HARPOON((port + hp_intstat)) & PARITY) &&
  1770. (RD_HARPOON(port + hp_addstat) & SCSI_PAR_ERR)) {
  1771. WR_HARPOON(port + hp_scsisig, (SCSI_ACK + S_ILL_PH));
  1772. WR_HARPOON(port + hp_xferstat, 0);
  1773. WR_HARPOON(port + hp_fiforead, 0);
  1774. WR_HARPOON(port + hp_fifowrite, 0);
  1775. if (pCurrSCCB != NULL) {
  1776. pCurrSCCB->Sccb_scsimsg = SMPARITY;
  1777. }
  1778. message = 0x00;
  1779. do {
  1780. ACCEPT_MSG_ATN(port);
  1781. TimeOutLoop = 0;
  1782. while ((!(RD_HARPOON(port + hp_scsisig) & SCSI_REQ)) &&
  1783. (TimeOutLoop++ < 20000)) {
  1784. }
  1785. if (TimeOutLoop > 20000) {
  1786. WRW_HARPOON((port + hp_intstat), PARITY);
  1787. return message;
  1788. }
  1789. if ((RD_HARPOON(port + hp_scsisig) & S_SCSI_PHZ) !=
  1790. S_MSGI_PH) {
  1791. WRW_HARPOON((port + hp_intstat), PARITY);
  1792. return message;
  1793. }
  1794. WR_HARPOON(port + hp_portctrl_0, SCSI_PORT);
  1795. RD_HARPOON(port + hp_scsidata_0);
  1796. WR_HARPOON(port + hp_scsisig, (SCSI_ACK + S_ILL_PH));
  1797. } while (1);
  1798. }
  1799. WR_HARPOON(port + hp_scsisig, (SCSI_ACK + S_ILL_PH));
  1800. WR_HARPOON(port + hp_xferstat, 0);
  1801. WR_HARPOON(port + hp_fiforead, 0);
  1802. WR_HARPOON(port + hp_fifowrite, 0);
  1803. return message;
  1804. }
  1805. /*---------------------------------------------------------------------
  1806. *
  1807. * Function: FPT_ssel
  1808. *
  1809. * Description: Load up automation and select target device.
  1810. *
  1811. *---------------------------------------------------------------------*/
  1812. static void FPT_ssel(u32 port, unsigned char p_card)
  1813. {
  1814. unsigned char auto_loaded, i, target, *theCCB;
  1815. u32 cdb_reg;
  1816. struct sccb_card *CurrCard;
  1817. struct sccb *currSCCB;
  1818. struct sccb_mgr_tar_info *currTar_Info;
  1819. unsigned char lastTag, lun;
  1820. CurrCard = &FPT_BL_Card[p_card];
  1821. currSCCB = CurrCard->currentSCCB;
  1822. target = currSCCB->TargID;
  1823. currTar_Info = &FPT_sccbMgrTbl[p_card][target];
  1824. lastTag = CurrCard->tagQ_Lst;
  1825. ARAM_ACCESS(port);
  1826. if ((currTar_Info->TarStatus & TAR_TAG_Q_MASK) == TAG_Q_REJECT)
  1827. currSCCB->ControlByte &= ~F_USE_CMD_Q;
  1828. if (((CurrCard->globalFlags & F_CONLUN_IO) &&
  1829. ((currTar_Info->TarStatus & TAR_TAG_Q_MASK) != TAG_Q_TRYING)))
  1830. lun = currSCCB->Lun;
  1831. else
  1832. lun = 0;
  1833. if (CurrCard->globalFlags & F_TAG_STARTED) {
  1834. if (!(currSCCB->ControlByte & F_USE_CMD_Q)) {
  1835. if ((currTar_Info->TarLUN_CA == 0)
  1836. && ((currTar_Info->TarStatus & TAR_TAG_Q_MASK)
  1837. == TAG_Q_TRYING)) {
  1838. if (currTar_Info->TarTagQ_Cnt != 0) {
  1839. currTar_Info->TarLUNBusy[lun] = 1;
  1840. FPT_queueSelectFail(CurrCard, p_card);
  1841. SGRAM_ACCESS(port);
  1842. return;
  1843. }
  1844. else {
  1845. currTar_Info->TarLUNBusy[lun] = 1;
  1846. }
  1847. }
  1848. /*End non-tagged */
  1849. else {
  1850. currTar_Info->TarLUNBusy[lun] = 1;
  1851. }
  1852. }
  1853. /*!Use cmd Q Tagged */
  1854. else {
  1855. if (currTar_Info->TarLUN_CA == 1) {
  1856. FPT_queueSelectFail(CurrCard, p_card);
  1857. SGRAM_ACCESS(port);
  1858. return;
  1859. }
  1860. currTar_Info->TarLUNBusy[lun] = 1;
  1861. } /*else use cmd Q tagged */
  1862. }
  1863. /*if glob tagged started */
  1864. else {
  1865. currTar_Info->TarLUNBusy[lun] = 1;
  1866. }
  1867. if ((((CurrCard->globalFlags & F_CONLUN_IO) &&
  1868. ((currTar_Info->TarStatus & TAR_TAG_Q_MASK) != TAG_Q_TRYING))
  1869. || (!(currSCCB->ControlByte & F_USE_CMD_Q)))) {
  1870. if (CurrCard->discQCount >= QUEUE_DEPTH) {
  1871. currTar_Info->TarLUNBusy[lun] = 1;
  1872. FPT_queueSelectFail(CurrCard, p_card);
  1873. SGRAM_ACCESS(port);
  1874. return;
  1875. }
  1876. for (i = 1; i < QUEUE_DEPTH; i++) {
  1877. if (++lastTag >= QUEUE_DEPTH)
  1878. lastTag = 1;
  1879. if (CurrCard->discQ_Tbl[lastTag] == NULL) {
  1880. CurrCard->tagQ_Lst = lastTag;
  1881. currTar_Info->LunDiscQ_Idx[lun] = lastTag;
  1882. CurrCard->discQ_Tbl[lastTag] = currSCCB;
  1883. CurrCard->discQCount++;
  1884. break;
  1885. }
  1886. }
  1887. if (i == QUEUE_DEPTH) {
  1888. currTar_Info->TarLUNBusy[lun] = 1;
  1889. FPT_queueSelectFail(CurrCard, p_card);
  1890. SGRAM_ACCESS(port);
  1891. return;
  1892. }
  1893. }
  1894. auto_loaded = 0;
  1895. WR_HARPOON(port + hp_select_id, target);
  1896. WR_HARPOON(port + hp_gp_reg_3, target); /* Use by new automation logic */
  1897. if (currSCCB->OperationCode == RESET_COMMAND) {
  1898. WRW_HARPOON((port + ID_MSG_STRT), (MPM_OP + AMSG_OUT +
  1899. (currSCCB->
  1900. Sccb_idmsg & ~DISC_PRIV)));
  1901. WRW_HARPOON((port + ID_MSG_STRT + 2), BRH_OP + ALWAYS + NP);
  1902. currSCCB->Sccb_scsimsg = SMDEV_RESET;
  1903. WR_HARPOON(port + hp_autostart_3, (SELECT + SELCHK_STRT));
  1904. auto_loaded = 1;
  1905. currSCCB->Sccb_scsistat = SELECT_BDR_ST;
  1906. if (currTar_Info->TarEEValue & EE_SYNC_MASK) {
  1907. currTar_Info->TarSyncCtrl = 0;
  1908. currTar_Info->TarStatus &= ~TAR_SYNC_MASK;
  1909. }
  1910. if (currTar_Info->TarEEValue & EE_WIDE_SCSI) {
  1911. currTar_Info->TarStatus &= ~TAR_WIDE_MASK;
  1912. }
  1913. FPT_sssyncv(port, target, NARROW_SCSI, currTar_Info);
  1914. FPT_SccbMgrTableInitTarget(p_card, target);
  1915. }
  1916. else if (currSCCB->Sccb_scsistat == ABORT_ST) {
  1917. WRW_HARPOON((port + ID_MSG_STRT), (MPM_OP + AMSG_OUT +
  1918. (currSCCB->
  1919. Sccb_idmsg & ~DISC_PRIV)));
  1920. WRW_HARPOON((port + ID_MSG_STRT + 2), BRH_OP + ALWAYS + CMDPZ);
  1921. WRW_HARPOON((port + SYNC_MSGS + 0), (MPM_OP + AMSG_OUT +
  1922. (((unsigned
  1923. char)(currSCCB->
  1924. ControlByte &
  1925. TAG_TYPE_MASK)
  1926. >> 6) | (unsigned char)
  1927. 0x20)));
  1928. WRW_HARPOON((port + SYNC_MSGS + 2),
  1929. (MPM_OP + AMSG_OUT + currSCCB->Sccb_tag));
  1930. WRW_HARPOON((port + SYNC_MSGS + 4), (BRH_OP + ALWAYS + NP));
  1931. WR_HARPOON(port + hp_autostart_3, (SELECT + SELCHK_STRT));
  1932. auto_loaded = 1;
  1933. }
  1934. else if (!(currTar_Info->TarStatus & WIDE_NEGOCIATED)) {
  1935. auto_loaded = FPT_siwidn(port, p_card);
  1936. currSCCB->Sccb_scsistat = SELECT_WN_ST;
  1937. }
  1938. else if (!((currTar_Info->TarStatus & TAR_SYNC_MASK)
  1939. == SYNC_SUPPORTED)) {
  1940. auto_loaded = FPT_sisyncn(port, p_card, 0);
  1941. currSCCB->Sccb_scsistat = SELECT_SN_ST;
  1942. }
  1943. if (!auto_loaded) {
  1944. if (currSCCB->ControlByte & F_USE_CMD_Q) {
  1945. CurrCard->globalFlags |= F_TAG_STARTED;
  1946. if ((currTar_Info->TarStatus & TAR_TAG_Q_MASK)
  1947. == TAG_Q_REJECT) {
  1948. currSCCB->ControlByte &= ~F_USE_CMD_Q;
  1949. /* Fix up the start instruction with a jump to
  1950. Non-Tag-CMD handling */
  1951. WRW_HARPOON((port + ID_MSG_STRT),
  1952. BRH_OP + ALWAYS + NTCMD);
  1953. WRW_HARPOON((port + NON_TAG_ID_MSG),
  1954. (MPM_OP + AMSG_OUT +
  1955. currSCCB->Sccb_idmsg));
  1956. WR_HARPOON(port + hp_autostart_3,
  1957. (SELECT + SELCHK_STRT));
  1958. /* Setup our STATE so we know what happened when
  1959. the wheels fall off. */
  1960. currSCCB->Sccb_scsistat = SELECT_ST;
  1961. currTar_Info->TarLUNBusy[lun] = 1;
  1962. }
  1963. else {
  1964. WRW_HARPOON((port + ID_MSG_STRT),
  1965. (MPM_OP + AMSG_OUT +
  1966. currSCCB->Sccb_idmsg));
  1967. WRW_HARPOON((port + ID_MSG_STRT + 2),
  1968. (MPM_OP + AMSG_OUT +
  1969. (((unsigned char)(currSCCB->
  1970. ControlByte &
  1971. TAG_TYPE_MASK)
  1972. >> 6) | (unsigned char)0x20)));
  1973. for (i = 1; i < QUEUE_DEPTH; i++) {
  1974. if (++lastTag >= QUEUE_DEPTH)
  1975. lastTag = 1;
  1976. if (CurrCard->discQ_Tbl[lastTag] ==
  1977. NULL) {
  1978. WRW_HARPOON((port +
  1979. ID_MSG_STRT + 6),
  1980. (MPM_OP + AMSG_OUT +
  1981. lastTag));
  1982. CurrCard->tagQ_Lst = lastTag;
  1983. currSCCB->Sccb_tag = lastTag;
  1984. CurrCard->discQ_Tbl[lastTag] =
  1985. currSCCB;
  1986. CurrCard->discQCount++;
  1987. break;
  1988. }
  1989. }
  1990. if (i == QUEUE_DEPTH) {
  1991. currTar_Info->TarLUNBusy[lun] = 1;
  1992. FPT_queueSelectFail(CurrCard, p_card);
  1993. SGRAM_ACCESS(port);
  1994. return;
  1995. }
  1996. currSCCB->Sccb_scsistat = SELECT_Q_ST;
  1997. WR_HARPOON(port + hp_autostart_3,
  1998. (SELECT + SELCHK_STRT));
  1999. }
  2000. }
  2001. else {
  2002. WRW_HARPOON((port + ID_MSG_STRT),
  2003. BRH_OP + ALWAYS + NTCMD);
  2004. WRW_HARPOON((port + NON_TAG_ID_MSG),
  2005. (MPM_OP + AMSG_OUT + currSCCB->Sccb_idmsg));
  2006. currSCCB->Sccb_scsistat = SELECT_ST;
  2007. WR_HARPOON(port + hp_autostart_3,
  2008. (SELECT + SELCHK_STRT));
  2009. }
  2010. theCCB = (unsigned char *)&currSCCB->Cdb[0];
  2011. cdb_reg = port + CMD_STRT;
  2012. for (i = 0; i < currSCCB->CdbLength; i++) {
  2013. WRW_HARPOON(cdb_reg, (MPM_OP + ACOMMAND + *theCCB));
  2014. cdb_reg += 2;
  2015. theCCB++;
  2016. }
  2017. if (currSCCB->CdbLength != TWELVE_BYTE_CMD)
  2018. WRW_HARPOON(cdb_reg, (BRH_OP + ALWAYS + NP));
  2019. }
  2020. /* auto_loaded */
  2021. WRW_HARPOON((port + hp_fiforead), (unsigned short)0x00);
  2022. WR_HARPOON(port + hp_xferstat, 0x00);
  2023. WRW_HARPOON((port + hp_intstat), (PROG_HLT | TIMEOUT | SEL | BUS_FREE));
  2024. WR_HARPOON(port + hp_portctrl_0, (SCSI_PORT));
  2025. if (!(currSCCB->Sccb_MGRFlags & F_DEV_SELECTED)) {
  2026. WR_HARPOON(port + hp_scsictrl_0,
  2027. (SEL_TAR | ENA_ATN | ENA_RESEL | ENA_SCAM_SEL));
  2028. } else {
  2029. /* auto_loaded = (RD_HARPOON(port+hp_autostart_3) & (unsigned char)0x1F);
  2030. auto_loaded |= AUTO_IMMED; */
  2031. auto_loaded = AUTO_IMMED;
  2032. DISABLE_AUTO(port);
  2033. WR_HARPOON(port + hp_autostart_3, auto_loaded);
  2034. }
  2035. SGRAM_ACCESS(port);
  2036. }
  2037. /*---------------------------------------------------------------------
  2038. *
  2039. * Function: FPT_sres
  2040. *
  2041. * Description: Hookup the correct CCB and handle the incoming messages.
  2042. *
  2043. *---------------------------------------------------------------------*/
  2044. static void FPT_sres(u32 port, unsigned char p_card,
  2045. struct sccb_card *pCurrCard)
  2046. {
  2047. unsigned char our_target, message, lun = 0, tag, msgRetryCount;
  2048. struct sccb_mgr_tar_info *currTar_Info;
  2049. struct sccb *currSCCB;
  2050. if (pCurrCard->currentSCCB != NULL) {
  2051. currTar_Info =
  2052. &FPT_sccbMgrTbl[p_card][pCurrCard->currentSCCB->TargID];
  2053. DISABLE_AUTO(port);
  2054. WR_HARPOON((port + hp_scsictrl_0), (ENA_RESEL | ENA_SCAM_SEL));
  2055. currSCCB = pCurrCard->currentSCCB;
  2056. if (currSCCB->Sccb_scsistat == SELECT_WN_ST) {
  2057. currTar_Info->TarStatus &= ~TAR_WIDE_MASK;
  2058. currSCCB->Sccb_scsistat = BUS_FREE_ST;
  2059. }
  2060. if (currSCCB->Sccb_scsistat == SELECT_SN_ST) {
  2061. currTar_Info->TarStatus &= ~TAR_SYNC_MASK;
  2062. currSCCB->Sccb_scsistat = BUS_FREE_ST;
  2063. }
  2064. if (((pCurrCard->globalFlags & F_CONLUN_IO) &&
  2065. ((currTar_Info->TarStatus & TAR_TAG_Q_MASK) !=
  2066. TAG_Q_TRYING))) {
  2067. currTar_Info->TarLUNBusy[currSCCB->Lun] = 0;
  2068. if (currSCCB->Sccb_scsistat != ABORT_ST) {
  2069. pCurrCard->discQCount--;
  2070. pCurrCard->discQ_Tbl[currTar_Info->
  2071. LunDiscQ_Idx[currSCCB->
  2072. Lun]]
  2073. = NULL;
  2074. }
  2075. } else {
  2076. currTar_Info->TarLUNBusy[0] = 0;
  2077. if (currSCCB->Sccb_tag) {
  2078. if (currSCCB->Sccb_scsistat != ABORT_ST) {
  2079. pCurrCard->discQCount--;
  2080. pCurrCard->discQ_Tbl[currSCCB->
  2081. Sccb_tag] = NULL;
  2082. }
  2083. } else {
  2084. if (currSCCB->Sccb_scsistat != ABORT_ST) {
  2085. pCurrCard->discQCount--;
  2086. pCurrCard->discQ_Tbl[currTar_Info->
  2087. LunDiscQ_Idx[0]] =
  2088. NULL;
  2089. }
  2090. }
  2091. }
  2092. FPT_queueSelectFail(&FPT_BL_Card[p_card], p_card);
  2093. }
  2094. WRW_HARPOON((port + hp_fiforead), (unsigned short)0x00);
  2095. our_target = (unsigned char)(RD_HARPOON(port + hp_select_id) >> 4);
  2096. currTar_Info = &FPT_sccbMgrTbl[p_card][our_target];
  2097. msgRetryCount = 0;
  2098. do {
  2099. currTar_Info = &FPT_sccbMgrTbl[p_card][our_target];
  2100. tag = 0;
  2101. while (!(RD_HARPOON(port + hp_scsisig) & SCSI_REQ)) {
  2102. if (!(RD_HARPOON(port + hp_scsisig) & SCSI_BSY)) {
  2103. WRW_HARPOON((port + hp_intstat), PHASE);
  2104. return;
  2105. }
  2106. }
  2107. WRW_HARPOON((port + hp_intstat), PHASE);
  2108. if ((RD_HARPOON(port + hp_scsisig) & S_SCSI_PHZ) == S_MSGI_PH) {
  2109. message = FPT_sfm(port, pCurrCard->currentSCCB);
  2110. if (message) {
  2111. if (message <= (0x80 | LUN_MASK)) {
  2112. lun = message & (unsigned char)LUN_MASK;
  2113. if ((currTar_Info->
  2114. TarStatus & TAR_TAG_Q_MASK) ==
  2115. TAG_Q_TRYING) {
  2116. if (currTar_Info->TarTagQ_Cnt !=
  2117. 0) {
  2118. if (!
  2119. (currTar_Info->
  2120. TarLUN_CA)) {
  2121. ACCEPT_MSG(port); /*Release the ACK for ID msg. */
  2122. message =
  2123. FPT_sfm
  2124. (port,
  2125. pCurrCard->
  2126. currentSCCB);
  2127. if (message) {
  2128. ACCEPT_MSG
  2129. (port);
  2130. }
  2131. else
  2132. message
  2133. = 0;
  2134. if (message !=
  2135. 0) {
  2136. tag =
  2137. FPT_sfm
  2138. (port,
  2139. pCurrCard->
  2140. currentSCCB);
  2141. if (!
  2142. (tag))
  2143. message
  2144. =
  2145. 0;
  2146. }
  2147. }
  2148. /*C.A. exists! */
  2149. }
  2150. /*End Q cnt != 0 */
  2151. }
  2152. /*End Tag cmds supported! */
  2153. }
  2154. /*End valid ID message. */
  2155. else {
  2156. ACCEPT_MSG_ATN(port);
  2157. }
  2158. }
  2159. /* End good id message. */
  2160. else {
  2161. message = 0;
  2162. }
  2163. } else {
  2164. ACCEPT_MSG_ATN(port);
  2165. while (!
  2166. (RDW_HARPOON((port + hp_intstat)) &
  2167. (PHASE | RESET))
  2168. && !(RD_HARPOON(port + hp_scsisig) & SCSI_REQ)
  2169. && (RD_HARPOON(port + hp_scsisig) & SCSI_BSY)) ;
  2170. return;
  2171. }
  2172. if (message == 0) {
  2173. msgRetryCount++;
  2174. if (msgRetryCount == 1) {
  2175. FPT_SendMsg(port, SMPARITY);
  2176. } else {
  2177. FPT_SendMsg(port, SMDEV_RESET);
  2178. FPT_sssyncv(port, our_target, NARROW_SCSI,
  2179. currTar_Info);
  2180. if (FPT_sccbMgrTbl[p_card][our_target].
  2181. TarEEValue & EE_SYNC_MASK) {
  2182. FPT_sccbMgrTbl[p_card][our_target].
  2183. TarStatus &= ~TAR_SYNC_MASK;
  2184. }
  2185. if (FPT_sccbMgrTbl[p_card][our_target].
  2186. TarEEValue & EE_WIDE_SCSI) {
  2187. FPT_sccbMgrTbl[p_card][our_target].
  2188. TarStatus &= ~TAR_WIDE_MASK;
  2189. }
  2190. FPT_queueFlushTargSccb(p_card, our_target,
  2191. SCCB_COMPLETE);
  2192. FPT_SccbMgrTableInitTarget(p_card, our_target);
  2193. return;
  2194. }
  2195. }
  2196. } while (message == 0);
  2197. if (((pCurrCard->globalFlags & F_CONLUN_IO) &&
  2198. ((currTar_Info->TarStatus & TAR_TAG_Q_MASK) != TAG_Q_TRYING))) {
  2199. currTar_Info->TarLUNBusy[lun] = 1;
  2200. pCurrCard->currentSCCB =
  2201. pCurrCard->discQ_Tbl[currTar_Info->LunDiscQ_Idx[lun]];
  2202. if (pCurrCard->currentSCCB != NULL) {
  2203. ACCEPT_MSG(port);
  2204. } else {
  2205. ACCEPT_MSG_ATN(port);
  2206. }
  2207. } else {
  2208. currTar_Info->TarLUNBusy[0] = 1;
  2209. if (tag) {
  2210. if (pCurrCard->discQ_Tbl[tag] != NULL) {
  2211. pCurrCard->currentSCCB =
  2212. pCurrCard->discQ_Tbl[tag];
  2213. currTar_Info->TarTagQ_Cnt--;
  2214. ACCEPT_MSG(port);
  2215. } else {
  2216. ACCEPT_MSG_ATN(port);
  2217. }
  2218. } else {
  2219. pCurrCard->currentSCCB =
  2220. pCurrCard->discQ_Tbl[currTar_Info->LunDiscQ_Idx[0]];
  2221. if (pCurrCard->currentSCCB != NULL) {
  2222. ACCEPT_MSG(port);
  2223. } else {
  2224. ACCEPT_MSG_ATN(port);
  2225. }
  2226. }
  2227. }
  2228. if (pCurrCard->currentSCCB != NULL) {
  2229. if (pCurrCard->currentSCCB->Sccb_scsistat == ABORT_ST) {
  2230. /* During Abort Tag command, the target could have got re-selected
  2231. and completed the command. Check the select Q and remove the CCB
  2232. if it is in the Select Q */
  2233. FPT_queueFindSccb(pCurrCard->currentSCCB, p_card);
  2234. }
  2235. }
  2236. while (!(RDW_HARPOON((port + hp_intstat)) & (PHASE | RESET)) &&
  2237. !(RD_HARPOON(port + hp_scsisig) & SCSI_REQ) &&
  2238. (RD_HARPOON(port + hp_scsisig) & SCSI_BSY)) ;
  2239. }
  2240. static void FPT_SendMsg(u32 port, unsigned char message)
  2241. {
  2242. while (!(RD_HARPOON(port + hp_scsisig) & SCSI_REQ)) {
  2243. if (!(RD_HARPOON(port + hp_scsisig) & SCSI_BSY)) {
  2244. WRW_HARPOON((port + hp_intstat), PHASE);
  2245. return;
  2246. }
  2247. }
  2248. WRW_HARPOON((port + hp_intstat), PHASE);
  2249. if ((RD_HARPOON(port + hp_scsisig) & S_SCSI_PHZ) == S_MSGO_PH) {
  2250. WRW_HARPOON((port + hp_intstat),
  2251. (BUS_FREE | PHASE | XFER_CNT_0));
  2252. WR_HARPOON(port + hp_portctrl_0, SCSI_BUS_EN);
  2253. WR_HARPOON(port + hp_scsidata_0, message);
  2254. WR_HARPOON(port + hp_scsisig, (SCSI_ACK + S_ILL_PH));
  2255. ACCEPT_MSG(port);
  2256. WR_HARPOON(port + hp_portctrl_0, 0x00);
  2257. if ((message == SMABORT) || (message == SMDEV_RESET) ||
  2258. (message == SMABORT_TAG)) {
  2259. while (!
  2260. (RDW_HARPOON((port + hp_intstat)) &
  2261. (BUS_FREE | PHASE))) {
  2262. }
  2263. if (RDW_HARPOON((port + hp_intstat)) & BUS_FREE) {
  2264. WRW_HARPOON((port + hp_intstat), BUS_FREE);
  2265. }
  2266. }
  2267. }
  2268. }
  2269. /*---------------------------------------------------------------------
  2270. *
  2271. * Function: FPT_sdecm
  2272. *
  2273. * Description: Determine the proper response to the message from the
  2274. * target device.
  2275. *
  2276. *---------------------------------------------------------------------*/
  2277. static void FPT_sdecm(unsigned char message, u32 port, unsigned char p_card)
  2278. {
  2279. struct sccb *currSCCB;
  2280. struct sccb_card *CurrCard;
  2281. struct sccb_mgr_tar_info *currTar_Info;
  2282. CurrCard = &FPT_BL_Card[p_card];
  2283. currSCCB = CurrCard->currentSCCB;
  2284. currTar_Info = &FPT_sccbMgrTbl[p_card][currSCCB->TargID];
  2285. if (message == SMREST_DATA_PTR) {
  2286. if (!(currSCCB->Sccb_XferState & F_NO_DATA_YET)) {
  2287. currSCCB->Sccb_ATC = currSCCB->Sccb_savedATC;
  2288. FPT_hostDataXferRestart(currSCCB);
  2289. }
  2290. ACCEPT_MSG(port);
  2291. WR_HARPOON(port + hp_autostart_1,
  2292. (AUTO_IMMED + DISCONNECT_START));
  2293. }
  2294. else if (message == SMCMD_COMP) {
  2295. if (currSCCB->Sccb_scsistat == SELECT_Q_ST) {
  2296. currTar_Info->TarStatus &=
  2297. ~(unsigned char)TAR_TAG_Q_MASK;
  2298. currTar_Info->TarStatus |= (unsigned char)TAG_Q_REJECT;
  2299. }
  2300. ACCEPT_MSG(port);
  2301. }
  2302. else if ((message == SMNO_OP) || (message >= SMIDENT)
  2303. || (message == SMINIT_RECOVERY) || (message == SMREL_RECOVERY)) {
  2304. ACCEPT_MSG(port);
  2305. WR_HARPOON(port + hp_autostart_1,
  2306. (AUTO_IMMED + DISCONNECT_START));
  2307. }
  2308. else if (message == SMREJECT) {
  2309. if ((currSCCB->Sccb_scsistat == SELECT_SN_ST) ||
  2310. (currSCCB->Sccb_scsistat == SELECT_WN_ST) ||
  2311. ((currTar_Info->TarStatus & TAR_SYNC_MASK) == SYNC_TRYING)
  2312. || ((currTar_Info->TarStatus & TAR_TAG_Q_MASK) ==
  2313. TAG_Q_TRYING))
  2314. {
  2315. WRW_HARPOON((port + hp_intstat), BUS_FREE);
  2316. ACCEPT_MSG(port);
  2317. while ((!(RD_HARPOON(port + hp_scsisig) & SCSI_REQ)) &&
  2318. (!(RDW_HARPOON((port + hp_intstat)) & BUS_FREE)))
  2319. {
  2320. }
  2321. if (currSCCB->Lun == 0x00) {
  2322. if ((currSCCB->Sccb_scsistat == SELECT_SN_ST)) {
  2323. currTar_Info->TarStatus |=
  2324. (unsigned char)SYNC_SUPPORTED;
  2325. currTar_Info->TarEEValue &=
  2326. ~EE_SYNC_MASK;
  2327. }
  2328. else if ((currSCCB->Sccb_scsistat ==
  2329. SELECT_WN_ST)) {
  2330. currTar_Info->TarStatus =
  2331. (currTar_Info->
  2332. TarStatus & ~WIDE_ENABLED) |
  2333. WIDE_NEGOCIATED;
  2334. currTar_Info->TarEEValue &=
  2335. ~EE_WIDE_SCSI;
  2336. }
  2337. else if ((currTar_Info->
  2338. TarStatus & TAR_TAG_Q_MASK) ==
  2339. TAG_Q_TRYING) {
  2340. currTar_Info->TarStatus =
  2341. (currTar_Info->
  2342. TarStatus & ~(unsigned char)
  2343. TAR_TAG_Q_MASK) | TAG_Q_REJECT;
  2344. currSCCB->ControlByte &= ~F_USE_CMD_Q;
  2345. CurrCard->discQCount--;
  2346. CurrCard->discQ_Tbl[currSCCB->
  2347. Sccb_tag] = NULL;
  2348. currSCCB->Sccb_tag = 0x00;
  2349. }
  2350. }
  2351. if (RDW_HARPOON((port + hp_intstat)) & BUS_FREE) {
  2352. if (currSCCB->Lun == 0x00) {
  2353. WRW_HARPOON((port + hp_intstat),
  2354. BUS_FREE);
  2355. CurrCard->globalFlags |= F_NEW_SCCB_CMD;
  2356. }
  2357. }
  2358. else {
  2359. if ((CurrCard->globalFlags & F_CONLUN_IO) &&
  2360. ((currTar_Info->
  2361. TarStatus & TAR_TAG_Q_MASK) !=
  2362. TAG_Q_TRYING))
  2363. currTar_Info->TarLUNBusy[currSCCB->
  2364. Lun] = 1;
  2365. else
  2366. currTar_Info->TarLUNBusy[0] = 1;
  2367. currSCCB->ControlByte &=
  2368. ~(unsigned char)F_USE_CMD_Q;
  2369. WR_HARPOON(port + hp_autostart_1,
  2370. (AUTO_IMMED + DISCONNECT_START));
  2371. }
  2372. }
  2373. else {
  2374. ACCEPT_MSG(port);
  2375. while ((!(RD_HARPOON(port + hp_scsisig) & SCSI_REQ)) &&
  2376. (!(RDW_HARPOON((port + hp_intstat)) & BUS_FREE)))
  2377. {
  2378. }
  2379. if (!(RDW_HARPOON((port + hp_intstat)) & BUS_FREE)) {
  2380. WR_HARPOON(port + hp_autostart_1,
  2381. (AUTO_IMMED + DISCONNECT_START));
  2382. }
  2383. }
  2384. }
  2385. else if (message == SMEXT) {
  2386. ACCEPT_MSG(port);
  2387. FPT_shandem(port, p_card, currSCCB);
  2388. }
  2389. else if (message == SMIGNORWR) {
  2390. ACCEPT_MSG(port); /* ACK the RESIDUE MSG */
  2391. message = FPT_sfm(port, currSCCB);
  2392. if (currSCCB->Sccb_scsimsg != SMPARITY)
  2393. ACCEPT_MSG(port);
  2394. WR_HARPOON(port + hp_autostart_1,
  2395. (AUTO_IMMED + DISCONNECT_START));
  2396. }
  2397. else {
  2398. currSCCB->HostStatus = SCCB_PHASE_SEQUENCE_FAIL;
  2399. currSCCB->Sccb_scsimsg = SMREJECT;
  2400. ACCEPT_MSG_ATN(port);
  2401. WR_HARPOON(port + hp_autostart_1,
  2402. (AUTO_IMMED + DISCONNECT_START));
  2403. }
  2404. }
  2405. /*---------------------------------------------------------------------
  2406. *
  2407. * Function: FPT_shandem
  2408. *
  2409. * Description: Decide what to do with the extended message.
  2410. *
  2411. *---------------------------------------------------------------------*/
  2412. static void FPT_shandem(u32 port, unsigned char p_card, struct sccb *pCurrSCCB)
  2413. {
  2414. unsigned char length, message;
  2415. length = FPT_sfm(port, pCurrSCCB);
  2416. if (length) {
  2417. ACCEPT_MSG(port);
  2418. message = FPT_sfm(port, pCurrSCCB);
  2419. if (message) {
  2420. if (message == SMSYNC) {
  2421. if (length == 0x03) {
  2422. ACCEPT_MSG(port);
  2423. FPT_stsyncn(port, p_card);
  2424. } else {
  2425. pCurrSCCB->Sccb_scsimsg = SMREJECT;
  2426. ACCEPT_MSG_ATN(port);
  2427. }
  2428. } else if (message == SMWDTR) {
  2429. if (length == 0x02) {
  2430. ACCEPT_MSG(port);
  2431. FPT_stwidn(port, p_card);
  2432. } else {
  2433. pCurrSCCB->Sccb_scsimsg = SMREJECT;
  2434. ACCEPT_MSG_ATN(port);
  2435. WR_HARPOON(port + hp_autostart_1,
  2436. (AUTO_IMMED +
  2437. DISCONNECT_START));
  2438. }
  2439. } else {
  2440. pCurrSCCB->Sccb_scsimsg = SMREJECT;
  2441. ACCEPT_MSG_ATN(port);
  2442. WR_HARPOON(port + hp_autostart_1,
  2443. (AUTO_IMMED + DISCONNECT_START));
  2444. }
  2445. } else {
  2446. if (pCurrSCCB->Sccb_scsimsg != SMPARITY)
  2447. ACCEPT_MSG(port);
  2448. WR_HARPOON(port + hp_autostart_1,
  2449. (AUTO_IMMED + DISCONNECT_START));
  2450. }
  2451. } else {
  2452. if (pCurrSCCB->Sccb_scsimsg == SMPARITY)
  2453. WR_HARPOON(port + hp_autostart_1,
  2454. (AUTO_IMMED + DISCONNECT_START));
  2455. }
  2456. }
  2457. /*---------------------------------------------------------------------
  2458. *
  2459. * Function: FPT_sisyncn
  2460. *
  2461. * Description: Read in a message byte from the SCSI bus, and check
  2462. * for a parity error.
  2463. *
  2464. *---------------------------------------------------------------------*/
  2465. static unsigned char FPT_sisyncn(u32 port, unsigned char p_card,
  2466. unsigned char syncFlag)
  2467. {
  2468. struct sccb *currSCCB;
  2469. struct sccb_mgr_tar_info *currTar_Info;
  2470. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  2471. currTar_Info = &FPT_sccbMgrTbl[p_card][currSCCB->TargID];
  2472. if (!((currTar_Info->TarStatus & TAR_SYNC_MASK) == SYNC_TRYING)) {
  2473. WRW_HARPOON((port + ID_MSG_STRT),
  2474. (MPM_OP + AMSG_OUT +
  2475. (currSCCB->
  2476. Sccb_idmsg & ~(unsigned char)DISC_PRIV)));
  2477. WRW_HARPOON((port + ID_MSG_STRT + 2), BRH_OP + ALWAYS + CMDPZ);
  2478. WRW_HARPOON((port + SYNC_MSGS + 0),
  2479. (MPM_OP + AMSG_OUT + SMEXT));
  2480. WRW_HARPOON((port + SYNC_MSGS + 2), (MPM_OP + AMSG_OUT + 0x03));
  2481. WRW_HARPOON((port + SYNC_MSGS + 4),
  2482. (MPM_OP + AMSG_OUT + SMSYNC));
  2483. if ((currTar_Info->TarEEValue & EE_SYNC_MASK) == EE_SYNC_20MB)
  2484. WRW_HARPOON((port + SYNC_MSGS + 6),
  2485. (MPM_OP + AMSG_OUT + 12));
  2486. else if ((currTar_Info->TarEEValue & EE_SYNC_MASK) ==
  2487. EE_SYNC_10MB)
  2488. WRW_HARPOON((port + SYNC_MSGS + 6),
  2489. (MPM_OP + AMSG_OUT + 25));
  2490. else if ((currTar_Info->TarEEValue & EE_SYNC_MASK) ==
  2491. EE_SYNC_5MB)
  2492. WRW_HARPOON((port + SYNC_MSGS + 6),
  2493. (MPM_OP + AMSG_OUT + 50));
  2494. else
  2495. WRW_HARPOON((port + SYNC_MSGS + 6),
  2496. (MPM_OP + AMSG_OUT + 00));
  2497. WRW_HARPOON((port + SYNC_MSGS + 8), (RAT_OP));
  2498. WRW_HARPOON((port + SYNC_MSGS + 10),
  2499. (MPM_OP + AMSG_OUT + DEFAULT_OFFSET));
  2500. WRW_HARPOON((port + SYNC_MSGS + 12), (BRH_OP + ALWAYS + NP));
  2501. if (syncFlag == 0) {
  2502. WR_HARPOON(port + hp_autostart_3,
  2503. (SELECT + SELCHK_STRT));
  2504. currTar_Info->TarStatus =
  2505. ((currTar_Info->
  2506. TarStatus & ~(unsigned char)TAR_SYNC_MASK) |
  2507. (unsigned char)SYNC_TRYING);
  2508. } else {
  2509. WR_HARPOON(port + hp_autostart_3,
  2510. (AUTO_IMMED + CMD_ONLY_STRT));
  2511. }
  2512. return 1;
  2513. }
  2514. else {
  2515. currTar_Info->TarStatus |= (unsigned char)SYNC_SUPPORTED;
  2516. currTar_Info->TarEEValue &= ~EE_SYNC_MASK;
  2517. return 0;
  2518. }
  2519. }
  2520. /*---------------------------------------------------------------------
  2521. *
  2522. * Function: FPT_stsyncn
  2523. *
  2524. * Description: The has sent us a Sync Nego message so handle it as
  2525. * necessary.
  2526. *
  2527. *---------------------------------------------------------------------*/
  2528. static void FPT_stsyncn(u32 port, unsigned char p_card)
  2529. {
  2530. unsigned char sync_msg, offset, sync_reg, our_sync_msg;
  2531. struct sccb *currSCCB;
  2532. struct sccb_mgr_tar_info *currTar_Info;
  2533. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  2534. currTar_Info = &FPT_sccbMgrTbl[p_card][currSCCB->TargID];
  2535. sync_msg = FPT_sfm(port, currSCCB);
  2536. if ((sync_msg == 0x00) && (currSCCB->Sccb_scsimsg == SMPARITY)) {
  2537. WR_HARPOON(port + hp_autostart_1,
  2538. (AUTO_IMMED + DISCONNECT_START));
  2539. return;
  2540. }
  2541. ACCEPT_MSG(port);
  2542. offset = FPT_sfm(port, currSCCB);
  2543. if ((offset == 0x00) && (currSCCB->Sccb_scsimsg == SMPARITY)) {
  2544. WR_HARPOON(port + hp_autostart_1,
  2545. (AUTO_IMMED + DISCONNECT_START));
  2546. return;
  2547. }
  2548. if ((currTar_Info->TarEEValue & EE_SYNC_MASK) == EE_SYNC_20MB)
  2549. our_sync_msg = 12; /* Setup our Message to 20mb/s */
  2550. else if ((currTar_Info->TarEEValue & EE_SYNC_MASK) == EE_SYNC_10MB)
  2551. our_sync_msg = 25; /* Setup our Message to 10mb/s */
  2552. else if ((currTar_Info->TarEEValue & EE_SYNC_MASK) == EE_SYNC_5MB)
  2553. our_sync_msg = 50; /* Setup our Message to 5mb/s */
  2554. else
  2555. our_sync_msg = 0; /* Message = Async */
  2556. if (sync_msg < our_sync_msg) {
  2557. sync_msg = our_sync_msg; /*if faster, then set to max. */
  2558. }
  2559. if (offset == ASYNC)
  2560. sync_msg = ASYNC;
  2561. if (offset > MAX_OFFSET)
  2562. offset = MAX_OFFSET;
  2563. sync_reg = 0x00;
  2564. if (sync_msg > 12)
  2565. sync_reg = 0x20; /* Use 10MB/s */
  2566. if (sync_msg > 25)
  2567. sync_reg = 0x40; /* Use 6.6MB/s */
  2568. if (sync_msg > 38)
  2569. sync_reg = 0x60; /* Use 5MB/s */
  2570. if (sync_msg > 50)
  2571. sync_reg = 0x80; /* Use 4MB/s */
  2572. if (sync_msg > 62)
  2573. sync_reg = 0xA0; /* Use 3.33MB/s */
  2574. if (sync_msg > 75)
  2575. sync_reg = 0xC0; /* Use 2.85MB/s */
  2576. if (sync_msg > 87)
  2577. sync_reg = 0xE0; /* Use 2.5MB/s */
  2578. if (sync_msg > 100) {
  2579. sync_reg = 0x00; /* Use ASYNC */
  2580. offset = 0x00;
  2581. }
  2582. if (currTar_Info->TarStatus & WIDE_ENABLED)
  2583. sync_reg |= offset;
  2584. else
  2585. sync_reg |= (offset | NARROW_SCSI);
  2586. FPT_sssyncv(port, currSCCB->TargID, sync_reg, currTar_Info);
  2587. if (currSCCB->Sccb_scsistat == SELECT_SN_ST) {
  2588. ACCEPT_MSG(port);
  2589. currTar_Info->TarStatus = ((currTar_Info->TarStatus &
  2590. ~(unsigned char)TAR_SYNC_MASK) |
  2591. (unsigned char)SYNC_SUPPORTED);
  2592. WR_HARPOON(port + hp_autostart_1,
  2593. (AUTO_IMMED + DISCONNECT_START));
  2594. }
  2595. else {
  2596. ACCEPT_MSG_ATN(port);
  2597. FPT_sisyncr(port, sync_msg, offset);
  2598. currTar_Info->TarStatus = ((currTar_Info->TarStatus &
  2599. ~(unsigned char)TAR_SYNC_MASK) |
  2600. (unsigned char)SYNC_SUPPORTED);
  2601. }
  2602. }
  2603. /*---------------------------------------------------------------------
  2604. *
  2605. * Function: FPT_sisyncr
  2606. *
  2607. * Description: Answer the targets sync message.
  2608. *
  2609. *---------------------------------------------------------------------*/
  2610. static void FPT_sisyncr(u32 port, unsigned char sync_pulse,
  2611. unsigned char offset)
  2612. {
  2613. ARAM_ACCESS(port);
  2614. WRW_HARPOON((port + SYNC_MSGS + 0), (MPM_OP + AMSG_OUT + SMEXT));
  2615. WRW_HARPOON((port + SYNC_MSGS + 2), (MPM_OP + AMSG_OUT + 0x03));
  2616. WRW_HARPOON((port + SYNC_MSGS + 4), (MPM_OP + AMSG_OUT + SMSYNC));
  2617. WRW_HARPOON((port + SYNC_MSGS + 6), (MPM_OP + AMSG_OUT + sync_pulse));
  2618. WRW_HARPOON((port + SYNC_MSGS + 8), (RAT_OP));
  2619. WRW_HARPOON((port + SYNC_MSGS + 10), (MPM_OP + AMSG_OUT + offset));
  2620. WRW_HARPOON((port + SYNC_MSGS + 12), (BRH_OP + ALWAYS + NP));
  2621. SGRAM_ACCESS(port);
  2622. WR_HARPOON(port + hp_portctrl_0, SCSI_PORT);
  2623. WRW_HARPOON((port + hp_intstat), CLR_ALL_INT_1);
  2624. WR_HARPOON(port + hp_autostart_3, (AUTO_IMMED + CMD_ONLY_STRT));
  2625. while (!(RDW_HARPOON((port + hp_intstat)) & (BUS_FREE | AUTO_INT))) {
  2626. }
  2627. }
  2628. /*---------------------------------------------------------------------
  2629. *
  2630. * Function: FPT_siwidn
  2631. *
  2632. * Description: Read in a message byte from the SCSI bus, and check
  2633. * for a parity error.
  2634. *
  2635. *---------------------------------------------------------------------*/
  2636. static unsigned char FPT_siwidn(u32 port, unsigned char p_card)
  2637. {
  2638. struct sccb *currSCCB;
  2639. struct sccb_mgr_tar_info *currTar_Info;
  2640. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  2641. currTar_Info = &FPT_sccbMgrTbl[p_card][currSCCB->TargID];
  2642. if (!((currTar_Info->TarStatus & TAR_WIDE_MASK) == WIDE_NEGOCIATED)) {
  2643. WRW_HARPOON((port + ID_MSG_STRT),
  2644. (MPM_OP + AMSG_OUT +
  2645. (currSCCB->
  2646. Sccb_idmsg & ~(unsigned char)DISC_PRIV)));
  2647. WRW_HARPOON((port + ID_MSG_STRT + 2), BRH_OP + ALWAYS + CMDPZ);
  2648. WRW_HARPOON((port + SYNC_MSGS + 0),
  2649. (MPM_OP + AMSG_OUT + SMEXT));
  2650. WRW_HARPOON((port + SYNC_MSGS + 2), (MPM_OP + AMSG_OUT + 0x02));
  2651. WRW_HARPOON((port + SYNC_MSGS + 4),
  2652. (MPM_OP + AMSG_OUT + SMWDTR));
  2653. WRW_HARPOON((port + SYNC_MSGS + 6), (RAT_OP));
  2654. WRW_HARPOON((port + SYNC_MSGS + 8),
  2655. (MPM_OP + AMSG_OUT + SM16BIT));
  2656. WRW_HARPOON((port + SYNC_MSGS + 10), (BRH_OP + ALWAYS + NP));
  2657. WR_HARPOON(port + hp_autostart_3, (SELECT + SELCHK_STRT));
  2658. currTar_Info->TarStatus = ((currTar_Info->TarStatus &
  2659. ~(unsigned char)TAR_WIDE_MASK) |
  2660. (unsigned char)WIDE_ENABLED);
  2661. return 1;
  2662. }
  2663. else {
  2664. currTar_Info->TarStatus = ((currTar_Info->TarStatus &
  2665. ~(unsigned char)TAR_WIDE_MASK) |
  2666. WIDE_NEGOCIATED);
  2667. currTar_Info->TarEEValue &= ~EE_WIDE_SCSI;
  2668. return 0;
  2669. }
  2670. }
  2671. /*---------------------------------------------------------------------
  2672. *
  2673. * Function: FPT_stwidn
  2674. *
  2675. * Description: The has sent us a Wide Nego message so handle it as
  2676. * necessary.
  2677. *
  2678. *---------------------------------------------------------------------*/
  2679. static void FPT_stwidn(u32 port, unsigned char p_card)
  2680. {
  2681. unsigned char width;
  2682. struct sccb *currSCCB;
  2683. struct sccb_mgr_tar_info *currTar_Info;
  2684. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  2685. currTar_Info = &FPT_sccbMgrTbl[p_card][currSCCB->TargID];
  2686. width = FPT_sfm(port, currSCCB);
  2687. if ((width == 0x00) && (currSCCB->Sccb_scsimsg == SMPARITY)) {
  2688. WR_HARPOON(port + hp_autostart_1,
  2689. (AUTO_IMMED + DISCONNECT_START));
  2690. return;
  2691. }
  2692. if (!(currTar_Info->TarEEValue & EE_WIDE_SCSI))
  2693. width = 0;
  2694. if (width) {
  2695. currTar_Info->TarStatus |= WIDE_ENABLED;
  2696. width = 0;
  2697. } else {
  2698. width = NARROW_SCSI;
  2699. currTar_Info->TarStatus &= ~WIDE_ENABLED;
  2700. }
  2701. FPT_sssyncv(port, currSCCB->TargID, width, currTar_Info);
  2702. if (currSCCB->Sccb_scsistat == SELECT_WN_ST) {
  2703. currTar_Info->TarStatus |= WIDE_NEGOCIATED;
  2704. if (!
  2705. ((currTar_Info->TarStatus & TAR_SYNC_MASK) ==
  2706. SYNC_SUPPORTED)) {
  2707. ACCEPT_MSG_ATN(port);
  2708. ARAM_ACCESS(port);
  2709. FPT_sisyncn(port, p_card, 1);
  2710. currSCCB->Sccb_scsistat = SELECT_SN_ST;
  2711. SGRAM_ACCESS(port);
  2712. } else {
  2713. ACCEPT_MSG(port);
  2714. WR_HARPOON(port + hp_autostart_1,
  2715. (AUTO_IMMED + DISCONNECT_START));
  2716. }
  2717. }
  2718. else {
  2719. ACCEPT_MSG_ATN(port);
  2720. if (currTar_Info->TarEEValue & EE_WIDE_SCSI)
  2721. width = SM16BIT;
  2722. else
  2723. width = SM8BIT;
  2724. FPT_siwidr(port, width);
  2725. currTar_Info->TarStatus |= (WIDE_NEGOCIATED | WIDE_ENABLED);
  2726. }
  2727. }
  2728. /*---------------------------------------------------------------------
  2729. *
  2730. * Function: FPT_siwidr
  2731. *
  2732. * Description: Answer the targets Wide nego message.
  2733. *
  2734. *---------------------------------------------------------------------*/
  2735. static void FPT_siwidr(u32 port, unsigned char width)
  2736. {
  2737. ARAM_ACCESS(port);
  2738. WRW_HARPOON((port + SYNC_MSGS + 0), (MPM_OP + AMSG_OUT + SMEXT));
  2739. WRW_HARPOON((port + SYNC_MSGS + 2), (MPM_OP + AMSG_OUT + 0x02));
  2740. WRW_HARPOON((port + SYNC_MSGS + 4), (MPM_OP + AMSG_OUT + SMWDTR));
  2741. WRW_HARPOON((port + SYNC_MSGS + 6), (RAT_OP));
  2742. WRW_HARPOON((port + SYNC_MSGS + 8), (MPM_OP + AMSG_OUT + width));
  2743. WRW_HARPOON((port + SYNC_MSGS + 10), (BRH_OP + ALWAYS + NP));
  2744. SGRAM_ACCESS(port);
  2745. WR_HARPOON(port + hp_portctrl_0, SCSI_PORT);
  2746. WRW_HARPOON((port + hp_intstat), CLR_ALL_INT_1);
  2747. WR_HARPOON(port + hp_autostart_3, (AUTO_IMMED + CMD_ONLY_STRT));
  2748. while (!(RDW_HARPOON((port + hp_intstat)) & (BUS_FREE | AUTO_INT))) {
  2749. }
  2750. }
  2751. /*---------------------------------------------------------------------
  2752. *
  2753. * Function: FPT_sssyncv
  2754. *
  2755. * Description: Write the desired value to the Sync Register for the
  2756. * ID specified.
  2757. *
  2758. *---------------------------------------------------------------------*/
  2759. static void FPT_sssyncv(u32 p_port, unsigned char p_id,
  2760. unsigned char p_sync_value,
  2761. struct sccb_mgr_tar_info *currTar_Info)
  2762. {
  2763. unsigned char index;
  2764. index = p_id;
  2765. switch (index) {
  2766. case 0:
  2767. index = 12; /* hp_synctarg_0 */
  2768. break;
  2769. case 1:
  2770. index = 13; /* hp_synctarg_1 */
  2771. break;
  2772. case 2:
  2773. index = 14; /* hp_synctarg_2 */
  2774. break;
  2775. case 3:
  2776. index = 15; /* hp_synctarg_3 */
  2777. break;
  2778. case 4:
  2779. index = 8; /* hp_synctarg_4 */
  2780. break;
  2781. case 5:
  2782. index = 9; /* hp_synctarg_5 */
  2783. break;
  2784. case 6:
  2785. index = 10; /* hp_synctarg_6 */
  2786. break;
  2787. case 7:
  2788. index = 11; /* hp_synctarg_7 */
  2789. break;
  2790. case 8:
  2791. index = 4; /* hp_synctarg_8 */
  2792. break;
  2793. case 9:
  2794. index = 5; /* hp_synctarg_9 */
  2795. break;
  2796. case 10:
  2797. index = 6; /* hp_synctarg_10 */
  2798. break;
  2799. case 11:
  2800. index = 7; /* hp_synctarg_11 */
  2801. break;
  2802. case 12:
  2803. index = 0; /* hp_synctarg_12 */
  2804. break;
  2805. case 13:
  2806. index = 1; /* hp_synctarg_13 */
  2807. break;
  2808. case 14:
  2809. index = 2; /* hp_synctarg_14 */
  2810. break;
  2811. case 15:
  2812. index = 3; /* hp_synctarg_15 */
  2813. }
  2814. WR_HARPOON(p_port + hp_synctarg_base + index, p_sync_value);
  2815. currTar_Info->TarSyncCtrl = p_sync_value;
  2816. }
  2817. /*---------------------------------------------------------------------
  2818. *
  2819. * Function: FPT_sresb
  2820. *
  2821. * Description: Reset the desired card's SCSI bus.
  2822. *
  2823. *---------------------------------------------------------------------*/
  2824. static void FPT_sresb(u32 port, unsigned char p_card)
  2825. {
  2826. unsigned char scsiID, i;
  2827. struct sccb_mgr_tar_info *currTar_Info;
  2828. WR_HARPOON(port + hp_page_ctrl,
  2829. (RD_HARPOON(port + hp_page_ctrl) | G_INT_DISABLE));
  2830. WRW_HARPOON((port + hp_intstat), CLR_ALL_INT);
  2831. WR_HARPOON(port + hp_scsictrl_0, SCSI_RST);
  2832. scsiID = RD_HARPOON(port + hp_seltimeout);
  2833. WR_HARPOON(port + hp_seltimeout, TO_5ms);
  2834. WRW_HARPOON((port + hp_intstat), TIMEOUT);
  2835. WR_HARPOON(port + hp_portctrl_0, (SCSI_PORT | START_TO));
  2836. while (!(RDW_HARPOON((port + hp_intstat)) & TIMEOUT)) {
  2837. }
  2838. WR_HARPOON(port + hp_seltimeout, scsiID);
  2839. WR_HARPOON(port + hp_scsictrl_0, ENA_SCAM_SEL);
  2840. FPT_Wait(port, TO_5ms);
  2841. WRW_HARPOON((port + hp_intstat), CLR_ALL_INT);
  2842. WR_HARPOON(port + hp_int_mask, (RD_HARPOON(port + hp_int_mask) | 0x00));
  2843. for (scsiID = 0; scsiID < MAX_SCSI_TAR; scsiID++) {
  2844. currTar_Info = &FPT_sccbMgrTbl[p_card][scsiID];
  2845. if (currTar_Info->TarEEValue & EE_SYNC_MASK) {
  2846. currTar_Info->TarSyncCtrl = 0;
  2847. currTar_Info->TarStatus &= ~TAR_SYNC_MASK;
  2848. }
  2849. if (currTar_Info->TarEEValue & EE_WIDE_SCSI) {
  2850. currTar_Info->TarStatus &= ~TAR_WIDE_MASK;
  2851. }
  2852. FPT_sssyncv(port, scsiID, NARROW_SCSI, currTar_Info);
  2853. FPT_SccbMgrTableInitTarget(p_card, scsiID);
  2854. }
  2855. FPT_BL_Card[p_card].scanIndex = 0x00;
  2856. FPT_BL_Card[p_card].currentSCCB = NULL;
  2857. FPT_BL_Card[p_card].globalFlags &= ~(F_TAG_STARTED | F_HOST_XFER_ACT
  2858. | F_NEW_SCCB_CMD);
  2859. FPT_BL_Card[p_card].cmdCounter = 0x00;
  2860. FPT_BL_Card[p_card].discQCount = 0x00;
  2861. FPT_BL_Card[p_card].tagQ_Lst = 0x01;
  2862. for (i = 0; i < QUEUE_DEPTH; i++)
  2863. FPT_BL_Card[p_card].discQ_Tbl[i] = NULL;
  2864. WR_HARPOON(port + hp_page_ctrl,
  2865. (RD_HARPOON(port + hp_page_ctrl) & ~G_INT_DISABLE));
  2866. }
  2867. /*---------------------------------------------------------------------
  2868. *
  2869. * Function: FPT_ssenss
  2870. *
  2871. * Description: Setup for the Auto Sense command.
  2872. *
  2873. *---------------------------------------------------------------------*/
  2874. static void FPT_ssenss(struct sccb_card *pCurrCard)
  2875. {
  2876. unsigned char i;
  2877. struct sccb *currSCCB;
  2878. currSCCB = pCurrCard->currentSCCB;
  2879. currSCCB->Save_CdbLen = currSCCB->CdbLength;
  2880. for (i = 0; i < 6; i++) {
  2881. currSCCB->Save_Cdb[i] = currSCCB->Cdb[i];
  2882. }
  2883. currSCCB->CdbLength = SIX_BYTE_CMD;
  2884. currSCCB->Cdb[0] = SCSI_REQUEST_SENSE;
  2885. currSCCB->Cdb[1] = currSCCB->Cdb[1] & (unsigned char)0xE0; /*Keep LUN. */
  2886. currSCCB->Cdb[2] = 0x00;
  2887. currSCCB->Cdb[3] = 0x00;
  2888. currSCCB->Cdb[4] = currSCCB->RequestSenseLength;
  2889. currSCCB->Cdb[5] = 0x00;
  2890. currSCCB->Sccb_XferCnt = (u32)currSCCB->RequestSenseLength;
  2891. currSCCB->Sccb_ATC = 0x00;
  2892. currSCCB->Sccb_XferState |= F_AUTO_SENSE;
  2893. currSCCB->Sccb_XferState &= ~F_SG_XFER;
  2894. currSCCB->Sccb_idmsg = currSCCB->Sccb_idmsg & ~(unsigned char)DISC_PRIV;
  2895. currSCCB->ControlByte = 0x00;
  2896. currSCCB->Sccb_MGRFlags &= F_STATUSLOADED;
  2897. }
  2898. /*---------------------------------------------------------------------
  2899. *
  2900. * Function: FPT_sxfrp
  2901. *
  2902. * Description: Transfer data into the bit bucket until the device
  2903. * decides to switch phase.
  2904. *
  2905. *---------------------------------------------------------------------*/
  2906. static void FPT_sxfrp(u32 p_port, unsigned char p_card)
  2907. {
  2908. unsigned char curr_phz;
  2909. DISABLE_AUTO(p_port);
  2910. if (FPT_BL_Card[p_card].globalFlags & F_HOST_XFER_ACT) {
  2911. FPT_hostDataXferAbort(p_port, p_card,
  2912. FPT_BL_Card[p_card].currentSCCB);
  2913. }
  2914. /* If the Automation handled the end of the transfer then do not
  2915. match the phase or we will get out of sync with the ISR. */
  2916. if (RDW_HARPOON((p_port + hp_intstat)) &
  2917. (BUS_FREE | XFER_CNT_0 | AUTO_INT))
  2918. return;
  2919. WR_HARPOON(p_port + hp_xfercnt_0, 0x00);
  2920. curr_phz = RD_HARPOON(p_port + hp_scsisig) & (unsigned char)S_SCSI_PHZ;
  2921. WRW_HARPOON((p_port + hp_intstat), XFER_CNT_0);
  2922. WR_HARPOON(p_port + hp_scsisig, curr_phz);
  2923. while (!(RDW_HARPOON((p_port + hp_intstat)) & (BUS_FREE | RESET)) &&
  2924. (curr_phz ==
  2925. (RD_HARPOON(p_port + hp_scsisig) & (unsigned char)S_SCSI_PHZ)))
  2926. {
  2927. if (curr_phz & (unsigned char)SCSI_IOBIT) {
  2928. WR_HARPOON(p_port + hp_portctrl_0,
  2929. (SCSI_PORT | HOST_PORT | SCSI_INBIT));
  2930. if (!(RD_HARPOON(p_port + hp_xferstat) & FIFO_EMPTY)) {
  2931. RD_HARPOON(p_port + hp_fifodata_0);
  2932. }
  2933. } else {
  2934. WR_HARPOON(p_port + hp_portctrl_0,
  2935. (SCSI_PORT | HOST_PORT | HOST_WRT));
  2936. if (RD_HARPOON(p_port + hp_xferstat) & FIFO_EMPTY) {
  2937. WR_HARPOON(p_port + hp_fifodata_0, 0xFA);
  2938. }
  2939. }
  2940. } /* End of While loop for padding data I/O phase */
  2941. while (!(RDW_HARPOON((p_port + hp_intstat)) & (BUS_FREE | RESET))) {
  2942. if (RD_HARPOON(p_port + hp_scsisig) & SCSI_REQ)
  2943. break;
  2944. }
  2945. WR_HARPOON(p_port + hp_portctrl_0,
  2946. (SCSI_PORT | HOST_PORT | SCSI_INBIT));
  2947. while (!(RD_HARPOON(p_port + hp_xferstat) & FIFO_EMPTY)) {
  2948. RD_HARPOON(p_port + hp_fifodata_0);
  2949. }
  2950. if (!(RDW_HARPOON((p_port + hp_intstat)) & (BUS_FREE | RESET))) {
  2951. WR_HARPOON(p_port + hp_autostart_0,
  2952. (AUTO_IMMED + DISCONNECT_START));
  2953. while (!(RDW_HARPOON((p_port + hp_intstat)) & AUTO_INT)) {
  2954. }
  2955. if (RDW_HARPOON((p_port + hp_intstat)) &
  2956. (ICMD_COMP | ITAR_DISC))
  2957. while (!
  2958. (RDW_HARPOON((p_port + hp_intstat)) &
  2959. (BUS_FREE | RSEL))) ;
  2960. }
  2961. }
  2962. /*---------------------------------------------------------------------
  2963. *
  2964. * Function: FPT_schkdd
  2965. *
  2966. * Description: Make sure data has been flushed from both FIFOs and abort
  2967. * the operations if necessary.
  2968. *
  2969. *---------------------------------------------------------------------*/
  2970. static void FPT_schkdd(u32 port, unsigned char p_card)
  2971. {
  2972. unsigned short TimeOutLoop;
  2973. unsigned char sPhase;
  2974. struct sccb *currSCCB;
  2975. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  2976. if ((currSCCB->Sccb_scsistat != DATA_OUT_ST) &&
  2977. (currSCCB->Sccb_scsistat != DATA_IN_ST)) {
  2978. return;
  2979. }
  2980. if (currSCCB->Sccb_XferState & F_ODD_BALL_CNT) {
  2981. currSCCB->Sccb_ATC += (currSCCB->Sccb_XferCnt - 1);
  2982. currSCCB->Sccb_XferCnt = 1;
  2983. currSCCB->Sccb_XferState &= ~F_ODD_BALL_CNT;
  2984. WRW_HARPOON((port + hp_fiforead), (unsigned short)0x00);
  2985. WR_HARPOON(port + hp_xferstat, 0x00);
  2986. }
  2987. else {
  2988. currSCCB->Sccb_ATC += currSCCB->Sccb_XferCnt;
  2989. currSCCB->Sccb_XferCnt = 0;
  2990. }
  2991. if ((RDW_HARPOON((port + hp_intstat)) & PARITY) &&
  2992. (currSCCB->HostStatus == SCCB_COMPLETE)) {
  2993. currSCCB->HostStatus = SCCB_PARITY_ERR;
  2994. WRW_HARPOON((port + hp_intstat), PARITY);
  2995. }
  2996. FPT_hostDataXferAbort(port, p_card, currSCCB);
  2997. while (RD_HARPOON(port + hp_scsisig) & SCSI_ACK) {
  2998. }
  2999. TimeOutLoop = 0;
  3000. while (RD_HARPOON(port + hp_xferstat) & FIFO_EMPTY) {
  3001. if (RDW_HARPOON((port + hp_intstat)) & BUS_FREE) {
  3002. return;
  3003. }
  3004. if (RD_HARPOON(port + hp_offsetctr) & (unsigned char)0x1F) {
  3005. break;
  3006. }
  3007. if (RDW_HARPOON((port + hp_intstat)) & RESET) {
  3008. return;
  3009. }
  3010. if ((RD_HARPOON(port + hp_scsisig) & SCSI_REQ)
  3011. || (TimeOutLoop++ > 0x3000))
  3012. break;
  3013. }
  3014. sPhase = RD_HARPOON(port + hp_scsisig) & (SCSI_BSY | S_SCSI_PHZ);
  3015. if ((!(RD_HARPOON(port + hp_xferstat) & FIFO_EMPTY)) ||
  3016. (RD_HARPOON(port + hp_offsetctr) & (unsigned char)0x1F) ||
  3017. (sPhase == (SCSI_BSY | S_DATAO_PH)) ||
  3018. (sPhase == (SCSI_BSY | S_DATAI_PH))) {
  3019. WR_HARPOON(port + hp_portctrl_0, SCSI_PORT);
  3020. if (!(currSCCB->Sccb_XferState & F_ALL_XFERRED)) {
  3021. if (currSCCB->Sccb_XferState & F_HOST_XFER_DIR) {
  3022. FPT_phaseDataIn(port, p_card);
  3023. }
  3024. else {
  3025. FPT_phaseDataOut(port, p_card);
  3026. }
  3027. } else {
  3028. FPT_sxfrp(port, p_card);
  3029. if (!(RDW_HARPOON((port + hp_intstat)) &
  3030. (BUS_FREE | ICMD_COMP | ITAR_DISC | RESET))) {
  3031. WRW_HARPOON((port + hp_intstat), AUTO_INT);
  3032. FPT_phaseDecode(port, p_card);
  3033. }
  3034. }
  3035. }
  3036. else {
  3037. WR_HARPOON(port + hp_portctrl_0, 0x00);
  3038. }
  3039. }
  3040. /*---------------------------------------------------------------------
  3041. *
  3042. * Function: FPT_sinits
  3043. *
  3044. * Description: Setup SCCB manager fields in this SCCB.
  3045. *
  3046. *---------------------------------------------------------------------*/
  3047. static void FPT_sinits(struct sccb *p_sccb, unsigned char p_card)
  3048. {
  3049. struct sccb_mgr_tar_info *currTar_Info;
  3050. if ((p_sccb->TargID >= MAX_SCSI_TAR) || (p_sccb->Lun >= MAX_LUN)) {
  3051. return;
  3052. }
  3053. currTar_Info = &FPT_sccbMgrTbl[p_card][p_sccb->TargID];
  3054. p_sccb->Sccb_XferState = 0x00;
  3055. p_sccb->Sccb_XferCnt = p_sccb->DataLength;
  3056. if ((p_sccb->OperationCode == SCATTER_GATHER_COMMAND) ||
  3057. (p_sccb->OperationCode == RESIDUAL_SG_COMMAND)) {
  3058. p_sccb->Sccb_SGoffset = 0;
  3059. p_sccb->Sccb_XferState = F_SG_XFER;
  3060. p_sccb->Sccb_XferCnt = 0x00;
  3061. }
  3062. if (p_sccb->DataLength == 0x00)
  3063. p_sccb->Sccb_XferState |= F_ALL_XFERRED;
  3064. if (p_sccb->ControlByte & F_USE_CMD_Q) {
  3065. if ((currTar_Info->TarStatus & TAR_TAG_Q_MASK) == TAG_Q_REJECT)
  3066. p_sccb->ControlByte &= ~F_USE_CMD_Q;
  3067. else
  3068. currTar_Info->TarStatus |= TAG_Q_TRYING;
  3069. }
  3070. /* For !single SCSI device in system & device allow Disconnect
  3071. or command is tag_q type then send Cmd with Disconnect Enable
  3072. else send Cmd with Disconnect Disable */
  3073. /*
  3074. if (((!(FPT_BL_Card[p_card].globalFlags & F_SINGLE_DEVICE)) &&
  3075. (currTar_Info->TarStatus & TAR_ALLOW_DISC)) ||
  3076. (currTar_Info->TarStatus & TAG_Q_TRYING)) {
  3077. */
  3078. if ((currTar_Info->TarStatus & TAR_ALLOW_DISC) ||
  3079. (currTar_Info->TarStatus & TAG_Q_TRYING)) {
  3080. p_sccb->Sccb_idmsg =
  3081. (unsigned char)(SMIDENT | DISC_PRIV) | p_sccb->Lun;
  3082. }
  3083. else {
  3084. p_sccb->Sccb_idmsg = (unsigned char)SMIDENT | p_sccb->Lun;
  3085. }
  3086. p_sccb->HostStatus = 0x00;
  3087. p_sccb->TargetStatus = 0x00;
  3088. p_sccb->Sccb_tag = 0x00;
  3089. p_sccb->Sccb_MGRFlags = 0x00;
  3090. p_sccb->Sccb_sgseg = 0x00;
  3091. p_sccb->Sccb_ATC = 0x00;
  3092. p_sccb->Sccb_savedATC = 0x00;
  3093. /*
  3094. p_sccb->SccbVirtDataPtr = 0x00;
  3095. p_sccb->Sccb_forwardlink = NULL;
  3096. p_sccb->Sccb_backlink = NULL;
  3097. */
  3098. p_sccb->Sccb_scsistat = BUS_FREE_ST;
  3099. p_sccb->SccbStatus = SCCB_IN_PROCESS;
  3100. p_sccb->Sccb_scsimsg = SMNO_OP;
  3101. }
  3102. /*---------------------------------------------------------------------
  3103. *
  3104. * Function: Phase Decode
  3105. *
  3106. * Description: Determine the phase and call the appropriate function.
  3107. *
  3108. *---------------------------------------------------------------------*/
  3109. static void FPT_phaseDecode(u32 p_port, unsigned char p_card)
  3110. {
  3111. unsigned char phase_ref;
  3112. void (*phase) (u32, unsigned char);
  3113. DISABLE_AUTO(p_port);
  3114. phase_ref =
  3115. (unsigned char)(RD_HARPOON(p_port + hp_scsisig) & S_SCSI_PHZ);
  3116. phase = FPT_s_PhaseTbl[phase_ref];
  3117. (*phase) (p_port, p_card); /* Call the correct phase func */
  3118. }
  3119. /*---------------------------------------------------------------------
  3120. *
  3121. * Function: Data Out Phase
  3122. *
  3123. * Description: Start up both the BusMaster and Xbow.
  3124. *
  3125. *---------------------------------------------------------------------*/
  3126. static void FPT_phaseDataOut(u32 port, unsigned char p_card)
  3127. {
  3128. struct sccb *currSCCB;
  3129. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  3130. if (currSCCB == NULL) {
  3131. return; /* Exit if No SCCB record */
  3132. }
  3133. currSCCB->Sccb_scsistat = DATA_OUT_ST;
  3134. currSCCB->Sccb_XferState &= ~(F_HOST_XFER_DIR | F_NO_DATA_YET);
  3135. WR_HARPOON(port + hp_portctrl_0, SCSI_PORT);
  3136. WRW_HARPOON((port + hp_intstat), XFER_CNT_0);
  3137. WR_HARPOON(port + hp_autostart_0, (END_DATA + END_DATA_START));
  3138. FPT_dataXferProcessor(port, &FPT_BL_Card[p_card]);
  3139. if (currSCCB->Sccb_XferCnt == 0) {
  3140. if ((currSCCB->ControlByte & SCCB_DATA_XFER_OUT) &&
  3141. (currSCCB->HostStatus == SCCB_COMPLETE))
  3142. currSCCB->HostStatus = SCCB_DATA_OVER_RUN;
  3143. FPT_sxfrp(port, p_card);
  3144. if (!(RDW_HARPOON((port + hp_intstat)) & (BUS_FREE | RESET)))
  3145. FPT_phaseDecode(port, p_card);
  3146. }
  3147. }
  3148. /*---------------------------------------------------------------------
  3149. *
  3150. * Function: Data In Phase
  3151. *
  3152. * Description: Startup the BusMaster and the XBOW.
  3153. *
  3154. *---------------------------------------------------------------------*/
  3155. static void FPT_phaseDataIn(u32 port, unsigned char p_card)
  3156. {
  3157. struct sccb *currSCCB;
  3158. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  3159. if (currSCCB == NULL) {
  3160. return; /* Exit if No SCCB record */
  3161. }
  3162. currSCCB->Sccb_scsistat = DATA_IN_ST;
  3163. currSCCB->Sccb_XferState |= F_HOST_XFER_DIR;
  3164. currSCCB->Sccb_XferState &= ~F_NO_DATA_YET;
  3165. WR_HARPOON(port + hp_portctrl_0, SCSI_PORT);
  3166. WRW_HARPOON((port + hp_intstat), XFER_CNT_0);
  3167. WR_HARPOON(port + hp_autostart_0, (END_DATA + END_DATA_START));
  3168. FPT_dataXferProcessor(port, &FPT_BL_Card[p_card]);
  3169. if (currSCCB->Sccb_XferCnt == 0) {
  3170. if ((currSCCB->ControlByte & SCCB_DATA_XFER_IN) &&
  3171. (currSCCB->HostStatus == SCCB_COMPLETE))
  3172. currSCCB->HostStatus = SCCB_DATA_OVER_RUN;
  3173. FPT_sxfrp(port, p_card);
  3174. if (!(RDW_HARPOON((port + hp_intstat)) & (BUS_FREE | RESET)))
  3175. FPT_phaseDecode(port, p_card);
  3176. }
  3177. }
  3178. /*---------------------------------------------------------------------
  3179. *
  3180. * Function: Command Phase
  3181. *
  3182. * Description: Load the CDB into the automation and start it up.
  3183. *
  3184. *---------------------------------------------------------------------*/
  3185. static void FPT_phaseCommand(u32 p_port, unsigned char p_card)
  3186. {
  3187. struct sccb *currSCCB;
  3188. u32 cdb_reg;
  3189. unsigned char i;
  3190. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  3191. if (currSCCB->OperationCode == RESET_COMMAND) {
  3192. currSCCB->HostStatus = SCCB_PHASE_SEQUENCE_FAIL;
  3193. currSCCB->CdbLength = SIX_BYTE_CMD;
  3194. }
  3195. WR_HARPOON(p_port + hp_scsisig, 0x00);
  3196. ARAM_ACCESS(p_port);
  3197. cdb_reg = p_port + CMD_STRT;
  3198. for (i = 0; i < currSCCB->CdbLength; i++) {
  3199. if (currSCCB->OperationCode == RESET_COMMAND)
  3200. WRW_HARPOON(cdb_reg, (MPM_OP + ACOMMAND + 0x00));
  3201. else
  3202. WRW_HARPOON(cdb_reg,
  3203. (MPM_OP + ACOMMAND + currSCCB->Cdb[i]));
  3204. cdb_reg += 2;
  3205. }
  3206. if (currSCCB->CdbLength != TWELVE_BYTE_CMD)
  3207. WRW_HARPOON(cdb_reg, (BRH_OP + ALWAYS + NP));
  3208. WR_HARPOON(p_port + hp_portctrl_0, (SCSI_PORT));
  3209. currSCCB->Sccb_scsistat = COMMAND_ST;
  3210. WR_HARPOON(p_port + hp_autostart_3, (AUTO_IMMED | CMD_ONLY_STRT));
  3211. SGRAM_ACCESS(p_port);
  3212. }
  3213. /*---------------------------------------------------------------------
  3214. *
  3215. * Function: Status phase
  3216. *
  3217. * Description: Bring in the status and command complete message bytes
  3218. *
  3219. *---------------------------------------------------------------------*/
  3220. static void FPT_phaseStatus(u32 port, unsigned char p_card)
  3221. {
  3222. /* Start-up the automation to finish off this command and let the
  3223. isr handle the interrupt for command complete when it comes in.
  3224. We could wait here for the interrupt to be generated?
  3225. */
  3226. WR_HARPOON(port + hp_scsisig, 0x00);
  3227. WR_HARPOON(port + hp_autostart_0, (AUTO_IMMED + END_DATA_START));
  3228. }
  3229. /*---------------------------------------------------------------------
  3230. *
  3231. * Function: Phase Message Out
  3232. *
  3233. * Description: Send out our message (if we have one) and handle whatever
  3234. * else is involed.
  3235. *
  3236. *---------------------------------------------------------------------*/
  3237. static void FPT_phaseMsgOut(u32 port, unsigned char p_card)
  3238. {
  3239. unsigned char message, scsiID;
  3240. struct sccb *currSCCB;
  3241. struct sccb_mgr_tar_info *currTar_Info;
  3242. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  3243. if (currSCCB != NULL) {
  3244. message = currSCCB->Sccb_scsimsg;
  3245. scsiID = currSCCB->TargID;
  3246. if (message == SMDEV_RESET) {
  3247. currTar_Info = &FPT_sccbMgrTbl[p_card][scsiID];
  3248. currTar_Info->TarSyncCtrl = 0;
  3249. FPT_sssyncv(port, scsiID, NARROW_SCSI, currTar_Info);
  3250. if (FPT_sccbMgrTbl[p_card][scsiID].
  3251. TarEEValue & EE_SYNC_MASK) {
  3252. FPT_sccbMgrTbl[p_card][scsiID].TarStatus &=
  3253. ~TAR_SYNC_MASK;
  3254. }
  3255. if (FPT_sccbMgrTbl[p_card][scsiID].
  3256. TarEEValue & EE_WIDE_SCSI) {
  3257. FPT_sccbMgrTbl[p_card][scsiID].TarStatus &=
  3258. ~TAR_WIDE_MASK;
  3259. }
  3260. FPT_queueFlushSccb(p_card, SCCB_COMPLETE);
  3261. FPT_SccbMgrTableInitTarget(p_card, scsiID);
  3262. } else if (currSCCB->Sccb_scsistat == ABORT_ST) {
  3263. currSCCB->HostStatus = SCCB_COMPLETE;
  3264. if (FPT_BL_Card[p_card].discQ_Tbl[currSCCB->Sccb_tag] !=
  3265. NULL) {
  3266. FPT_BL_Card[p_card].discQ_Tbl[currSCCB->
  3267. Sccb_tag] = NULL;
  3268. FPT_sccbMgrTbl[p_card][scsiID].TarTagQ_Cnt--;
  3269. }
  3270. }
  3271. else if (currSCCB->Sccb_scsistat < COMMAND_ST) {
  3272. if (message == SMNO_OP) {
  3273. currSCCB->Sccb_MGRFlags |= F_DEV_SELECTED;
  3274. FPT_ssel(port, p_card);
  3275. return;
  3276. }
  3277. } else {
  3278. if (message == SMABORT)
  3279. FPT_queueFlushSccb(p_card, SCCB_COMPLETE);
  3280. }
  3281. } else {
  3282. message = SMABORT;
  3283. }
  3284. WRW_HARPOON((port + hp_intstat), (BUS_FREE | PHASE | XFER_CNT_0));
  3285. WR_HARPOON(port + hp_portctrl_0, SCSI_BUS_EN);
  3286. WR_HARPOON(port + hp_scsidata_0, message);
  3287. WR_HARPOON(port + hp_scsisig, (SCSI_ACK + S_ILL_PH));
  3288. ACCEPT_MSG(port);
  3289. WR_HARPOON(port + hp_portctrl_0, 0x00);
  3290. if ((message == SMABORT) || (message == SMDEV_RESET) ||
  3291. (message == SMABORT_TAG)) {
  3292. while (!(RDW_HARPOON((port + hp_intstat)) & (BUS_FREE | PHASE))) {
  3293. }
  3294. if (RDW_HARPOON((port + hp_intstat)) & BUS_FREE) {
  3295. WRW_HARPOON((port + hp_intstat), BUS_FREE);
  3296. if (currSCCB != NULL) {
  3297. if ((FPT_BL_Card[p_card].
  3298. globalFlags & F_CONLUN_IO)
  3299. &&
  3300. ((FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3301. TarStatus & TAR_TAG_Q_MASK) !=
  3302. TAG_Q_TRYING))
  3303. FPT_sccbMgrTbl[p_card][currSCCB->
  3304. TargID].
  3305. TarLUNBusy[currSCCB->Lun] = 0;
  3306. else
  3307. FPT_sccbMgrTbl[p_card][currSCCB->
  3308. TargID].
  3309. TarLUNBusy[0] = 0;
  3310. FPT_queueCmdComplete(&FPT_BL_Card[p_card],
  3311. currSCCB, p_card);
  3312. }
  3313. else {
  3314. FPT_BL_Card[p_card].globalFlags |=
  3315. F_NEW_SCCB_CMD;
  3316. }
  3317. }
  3318. else {
  3319. FPT_sxfrp(port, p_card);
  3320. }
  3321. }
  3322. else {
  3323. if (message == SMPARITY) {
  3324. currSCCB->Sccb_scsimsg = SMNO_OP;
  3325. WR_HARPOON(port + hp_autostart_1,
  3326. (AUTO_IMMED + DISCONNECT_START));
  3327. } else {
  3328. FPT_sxfrp(port, p_card);
  3329. }
  3330. }
  3331. }
  3332. /*---------------------------------------------------------------------
  3333. *
  3334. * Function: Message In phase
  3335. *
  3336. * Description: Bring in the message and determine what to do with it.
  3337. *
  3338. *---------------------------------------------------------------------*/
  3339. static void FPT_phaseMsgIn(u32 port, unsigned char p_card)
  3340. {
  3341. unsigned char message;
  3342. struct sccb *currSCCB;
  3343. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  3344. if (FPT_BL_Card[p_card].globalFlags & F_HOST_XFER_ACT) {
  3345. FPT_phaseChkFifo(port, p_card);
  3346. }
  3347. message = RD_HARPOON(port + hp_scsidata_0);
  3348. if ((message == SMDISC) || (message == SMSAVE_DATA_PTR)) {
  3349. WR_HARPOON(port + hp_autostart_1,
  3350. (AUTO_IMMED + END_DATA_START));
  3351. }
  3352. else {
  3353. message = FPT_sfm(port, currSCCB);
  3354. if (message) {
  3355. FPT_sdecm(message, port, p_card);
  3356. } else {
  3357. if (currSCCB->Sccb_scsimsg != SMPARITY)
  3358. ACCEPT_MSG(port);
  3359. WR_HARPOON(port + hp_autostart_1,
  3360. (AUTO_IMMED + DISCONNECT_START));
  3361. }
  3362. }
  3363. }
  3364. /*---------------------------------------------------------------------
  3365. *
  3366. * Function: Illegal phase
  3367. *
  3368. * Description: Target switched to some illegal phase, so all we can do
  3369. * is report an error back to the host (if that is possible)
  3370. * and send an ABORT message to the misbehaving target.
  3371. *
  3372. *---------------------------------------------------------------------*/
  3373. static void FPT_phaseIllegal(u32 port, unsigned char p_card)
  3374. {
  3375. struct sccb *currSCCB;
  3376. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  3377. WR_HARPOON(port + hp_scsisig, RD_HARPOON(port + hp_scsisig));
  3378. if (currSCCB != NULL) {
  3379. currSCCB->HostStatus = SCCB_PHASE_SEQUENCE_FAIL;
  3380. currSCCB->Sccb_scsistat = ABORT_ST;
  3381. currSCCB->Sccb_scsimsg = SMABORT;
  3382. }
  3383. ACCEPT_MSG_ATN(port);
  3384. }
  3385. /*---------------------------------------------------------------------
  3386. *
  3387. * Function: Phase Check FIFO
  3388. *
  3389. * Description: Make sure data has been flushed from both FIFOs and abort
  3390. * the operations if necessary.
  3391. *
  3392. *---------------------------------------------------------------------*/
  3393. static void FPT_phaseChkFifo(u32 port, unsigned char p_card)
  3394. {
  3395. u32 xfercnt;
  3396. struct sccb *currSCCB;
  3397. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  3398. if (currSCCB->Sccb_scsistat == DATA_IN_ST) {
  3399. while ((!(RD_HARPOON(port + hp_xferstat) & FIFO_EMPTY)) &&
  3400. (RD_HARPOON(port + hp_ext_status) & BM_CMD_BUSY)) {
  3401. }
  3402. if (!(RD_HARPOON(port + hp_xferstat) & FIFO_EMPTY)) {
  3403. currSCCB->Sccb_ATC += currSCCB->Sccb_XferCnt;
  3404. currSCCB->Sccb_XferCnt = 0;
  3405. if ((RDW_HARPOON((port + hp_intstat)) & PARITY) &&
  3406. (currSCCB->HostStatus == SCCB_COMPLETE)) {
  3407. currSCCB->HostStatus = SCCB_PARITY_ERR;
  3408. WRW_HARPOON((port + hp_intstat), PARITY);
  3409. }
  3410. FPT_hostDataXferAbort(port, p_card, currSCCB);
  3411. FPT_dataXferProcessor(port, &FPT_BL_Card[p_card]);
  3412. while ((!(RD_HARPOON(port + hp_xferstat) & FIFO_EMPTY))
  3413. && (RD_HARPOON(port + hp_ext_status) &
  3414. BM_CMD_BUSY)) {
  3415. }
  3416. }
  3417. }
  3418. /*End Data In specific code. */
  3419. GET_XFER_CNT(port, xfercnt);
  3420. WR_HARPOON(port + hp_xfercnt_0, 0x00);
  3421. WR_HARPOON(port + hp_portctrl_0, 0x00);
  3422. currSCCB->Sccb_ATC += (currSCCB->Sccb_XferCnt - xfercnt);
  3423. currSCCB->Sccb_XferCnt = xfercnt;
  3424. if ((RDW_HARPOON((port + hp_intstat)) & PARITY) &&
  3425. (currSCCB->HostStatus == SCCB_COMPLETE)) {
  3426. currSCCB->HostStatus = SCCB_PARITY_ERR;
  3427. WRW_HARPOON((port + hp_intstat), PARITY);
  3428. }
  3429. FPT_hostDataXferAbort(port, p_card, currSCCB);
  3430. WR_HARPOON(port + hp_fifowrite, 0x00);
  3431. WR_HARPOON(port + hp_fiforead, 0x00);
  3432. WR_HARPOON(port + hp_xferstat, 0x00);
  3433. WRW_HARPOON((port + hp_intstat), XFER_CNT_0);
  3434. }
  3435. /*---------------------------------------------------------------------
  3436. *
  3437. * Function: Phase Bus Free
  3438. *
  3439. * Description: We just went bus free so figure out if it was
  3440. * because of command complete or from a disconnect.
  3441. *
  3442. *---------------------------------------------------------------------*/
  3443. static void FPT_phaseBusFree(u32 port, unsigned char p_card)
  3444. {
  3445. struct sccb *currSCCB;
  3446. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  3447. if (currSCCB != NULL) {
  3448. DISABLE_AUTO(port);
  3449. if (currSCCB->OperationCode == RESET_COMMAND) {
  3450. if ((FPT_BL_Card[p_card].globalFlags & F_CONLUN_IO) &&
  3451. ((FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3452. TarStatus & TAR_TAG_Q_MASK) != TAG_Q_TRYING))
  3453. FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3454. TarLUNBusy[currSCCB->Lun] = 0;
  3455. else
  3456. FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3457. TarLUNBusy[0] = 0;
  3458. FPT_queueCmdComplete(&FPT_BL_Card[p_card], currSCCB,
  3459. p_card);
  3460. FPT_queueSearchSelect(&FPT_BL_Card[p_card], p_card);
  3461. }
  3462. else if (currSCCB->Sccb_scsistat == SELECT_SN_ST) {
  3463. FPT_sccbMgrTbl[p_card][currSCCB->TargID].TarStatus |=
  3464. (unsigned char)SYNC_SUPPORTED;
  3465. FPT_sccbMgrTbl[p_card][currSCCB->TargID].TarEEValue &=
  3466. ~EE_SYNC_MASK;
  3467. }
  3468. else if (currSCCB->Sccb_scsistat == SELECT_WN_ST) {
  3469. FPT_sccbMgrTbl[p_card][currSCCB->TargID].TarStatus =
  3470. (FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3471. TarStatus & ~WIDE_ENABLED) | WIDE_NEGOCIATED;
  3472. FPT_sccbMgrTbl[p_card][currSCCB->TargID].TarEEValue &=
  3473. ~EE_WIDE_SCSI;
  3474. }
  3475. else if (currSCCB->Sccb_scsistat == SELECT_Q_ST) {
  3476. /* Make sure this is not a phony BUS_FREE. If we were
  3477. reselected or if BUSY is NOT on then this is a
  3478. valid BUS FREE. SRR Wednesday, 5/10/1995. */
  3479. if ((!(RD_HARPOON(port + hp_scsisig) & SCSI_BSY)) ||
  3480. (RDW_HARPOON((port + hp_intstat)) & RSEL)) {
  3481. FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3482. TarStatus &= ~TAR_TAG_Q_MASK;
  3483. FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3484. TarStatus |= TAG_Q_REJECT;
  3485. }
  3486. else {
  3487. return;
  3488. }
  3489. }
  3490. else {
  3491. currSCCB->Sccb_scsistat = BUS_FREE_ST;
  3492. if (!currSCCB->HostStatus) {
  3493. currSCCB->HostStatus = SCCB_PHASE_SEQUENCE_FAIL;
  3494. }
  3495. if ((FPT_BL_Card[p_card].globalFlags & F_CONLUN_IO) &&
  3496. ((FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3497. TarStatus & TAR_TAG_Q_MASK) != TAG_Q_TRYING))
  3498. FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3499. TarLUNBusy[currSCCB->Lun] = 0;
  3500. else
  3501. FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3502. TarLUNBusy[0] = 0;
  3503. FPT_queueCmdComplete(&FPT_BL_Card[p_card], currSCCB,
  3504. p_card);
  3505. return;
  3506. }
  3507. FPT_BL_Card[p_card].globalFlags |= F_NEW_SCCB_CMD;
  3508. } /*end if !=null */
  3509. }
  3510. /*---------------------------------------------------------------------
  3511. *
  3512. * Function: Auto Load Default Map
  3513. *
  3514. * Description: Load the Automation RAM with the defualt map values.
  3515. *
  3516. *---------------------------------------------------------------------*/
  3517. static void FPT_autoLoadDefaultMap(u32 p_port)
  3518. {
  3519. u32 map_addr;
  3520. ARAM_ACCESS(p_port);
  3521. map_addr = p_port + hp_aramBase;
  3522. WRW_HARPOON(map_addr, (MPM_OP + AMSG_OUT + 0xC0)); /*ID MESSAGE */
  3523. map_addr += 2;
  3524. WRW_HARPOON(map_addr, (MPM_OP + AMSG_OUT + 0x20)); /*SIMPLE TAG QUEUEING MSG */
  3525. map_addr += 2;
  3526. WRW_HARPOON(map_addr, RAT_OP); /*RESET ATTENTION */
  3527. map_addr += 2;
  3528. WRW_HARPOON(map_addr, (MPM_OP + AMSG_OUT + 0x00)); /*TAG ID MSG */
  3529. map_addr += 2;
  3530. WRW_HARPOON(map_addr, (MPM_OP + ACOMMAND + 0x00)); /*CDB BYTE 0 */
  3531. map_addr += 2;
  3532. WRW_HARPOON(map_addr, (MPM_OP + ACOMMAND + 0x00)); /*CDB BYTE 1 */
  3533. map_addr += 2;
  3534. WRW_HARPOON(map_addr, (MPM_OP + ACOMMAND + 0x00)); /*CDB BYTE 2 */
  3535. map_addr += 2;
  3536. WRW_HARPOON(map_addr, (MPM_OP + ACOMMAND + 0x00)); /*CDB BYTE 3 */
  3537. map_addr += 2;
  3538. WRW_HARPOON(map_addr, (MPM_OP + ACOMMAND + 0x00)); /*CDB BYTE 4 */
  3539. map_addr += 2;
  3540. WRW_HARPOON(map_addr, (MPM_OP + ACOMMAND + 0x00)); /*CDB BYTE 5 */
  3541. map_addr += 2;
  3542. WRW_HARPOON(map_addr, (MPM_OP + ACOMMAND + 0x00)); /*CDB BYTE 6 */
  3543. map_addr += 2;
  3544. WRW_HARPOON(map_addr, (MPM_OP + ACOMMAND + 0x00)); /*CDB BYTE 7 */
  3545. map_addr += 2;
  3546. WRW_HARPOON(map_addr, (MPM_OP + ACOMMAND + 0x00)); /*CDB BYTE 8 */
  3547. map_addr += 2;
  3548. WRW_HARPOON(map_addr, (MPM_OP + ACOMMAND + 0x00)); /*CDB BYTE 9 */
  3549. map_addr += 2;
  3550. WRW_HARPOON(map_addr, (MPM_OP + ACOMMAND + 0x00)); /*CDB BYTE 10 */
  3551. map_addr += 2;
  3552. WRW_HARPOON(map_addr, (MPM_OP + ACOMMAND + 0x00)); /*CDB BYTE 11 */
  3553. map_addr += 2;
  3554. WRW_HARPOON(map_addr, (CPE_OP + ADATA_OUT + DINT)); /*JUMP IF DATA OUT */
  3555. map_addr += 2;
  3556. WRW_HARPOON(map_addr, (TCB_OP + FIFO_0 + DI)); /*JUMP IF NO DATA IN FIFO */
  3557. map_addr += 2; /*This means AYNC DATA IN */
  3558. WRW_HARPOON(map_addr, (SSI_OP + SSI_IDO_STRT)); /*STOP AND INTERRUPT */
  3559. map_addr += 2;
  3560. WRW_HARPOON(map_addr, (CPE_OP + ADATA_IN + DINT)); /*JUMP IF NOT DATA IN PHZ */
  3561. map_addr += 2;
  3562. WRW_HARPOON(map_addr, (CPN_OP + AMSG_IN + ST)); /*IF NOT MSG IN CHECK 4 DATA IN */
  3563. map_addr += 2;
  3564. WRW_HARPOON(map_addr, (CRD_OP + SDATA + 0x02)); /*SAVE DATA PTR MSG? */
  3565. map_addr += 2;
  3566. WRW_HARPOON(map_addr, (BRH_OP + NOT_EQ + DC)); /*GO CHECK FOR DISCONNECT MSG */
  3567. map_addr += 2;
  3568. WRW_HARPOON(map_addr, (MRR_OP + SDATA + D_AR1)); /*SAVE DATA PTRS MSG */
  3569. map_addr += 2;
  3570. WRW_HARPOON(map_addr, (CPN_OP + AMSG_IN + ST)); /*IF NOT MSG IN CHECK DATA IN */
  3571. map_addr += 2;
  3572. WRW_HARPOON(map_addr, (CRD_OP + SDATA + 0x04)); /*DISCONNECT MSG? */
  3573. map_addr += 2;
  3574. WRW_HARPOON(map_addr, (BRH_OP + NOT_EQ + UNKNWN)); /*UKNKNOWN MSG */
  3575. map_addr += 2;
  3576. WRW_HARPOON(map_addr, (MRR_OP + SDATA + D_BUCKET)); /*XFER DISCONNECT MSG */
  3577. map_addr += 2;
  3578. WRW_HARPOON(map_addr, (SSI_OP + SSI_ITAR_DISC)); /*STOP AND INTERRUPT */
  3579. map_addr += 2;
  3580. WRW_HARPOON(map_addr, (CPN_OP + ASTATUS + UNKNWN)); /*JUMP IF NOT STATUS PHZ. */
  3581. map_addr += 2;
  3582. WRW_HARPOON(map_addr, (MRR_OP + SDATA + D_AR0)); /*GET STATUS BYTE */
  3583. map_addr += 2;
  3584. WRW_HARPOON(map_addr, (CPN_OP + AMSG_IN + CC)); /*ERROR IF NOT MSG IN PHZ */
  3585. map_addr += 2;
  3586. WRW_HARPOON(map_addr, (CRD_OP + SDATA + 0x00)); /*CHECK FOR CMD COMPLETE MSG. */
  3587. map_addr += 2;
  3588. WRW_HARPOON(map_addr, (BRH_OP + NOT_EQ + CC)); /*ERROR IF NOT CMD COMPLETE MSG. */
  3589. map_addr += 2;
  3590. WRW_HARPOON(map_addr, (MRR_OP + SDATA + D_BUCKET)); /*GET CMD COMPLETE MSG */
  3591. map_addr += 2;
  3592. WRW_HARPOON(map_addr, (SSI_OP + SSI_ICMD_COMP)); /*END OF COMMAND */
  3593. map_addr += 2;
  3594. WRW_HARPOON(map_addr, (SSI_OP + SSI_IUNKWN)); /*RECEIVED UNKNOWN MSG BYTE */
  3595. map_addr += 2;
  3596. WRW_HARPOON(map_addr, (SSI_OP + SSI_INO_CC)); /*NO COMMAND COMPLETE AFTER STATUS */
  3597. map_addr += 2;
  3598. WRW_HARPOON(map_addr, (SSI_OP + SSI_ITICKLE)); /*BIOS Tickled the Mgr */
  3599. map_addr += 2;
  3600. WRW_HARPOON(map_addr, (SSI_OP + SSI_IRFAIL)); /*EXPECTED ID/TAG MESSAGES AND */
  3601. map_addr += 2; /* DIDN'T GET ONE */
  3602. WRW_HARPOON(map_addr, (CRR_OP + AR3 + S_IDREG)); /* comp SCSI SEL ID & AR3 */
  3603. map_addr += 2;
  3604. WRW_HARPOON(map_addr, (BRH_OP + EQUAL + 0x00)); /*SEL ID OK then Conti. */
  3605. map_addr += 2;
  3606. WRW_HARPOON(map_addr, (SSI_OP + SSI_INO_CC)); /*NO COMMAND COMPLETE AFTER STATUS */
  3607. SGRAM_ACCESS(p_port);
  3608. }
  3609. /*---------------------------------------------------------------------
  3610. *
  3611. * Function: Auto Command Complete
  3612. *
  3613. * Description: Post command back to host and find another command
  3614. * to execute.
  3615. *
  3616. *---------------------------------------------------------------------*/
  3617. static void FPT_autoCmdCmplt(u32 p_port, unsigned char p_card)
  3618. {
  3619. struct sccb *currSCCB;
  3620. unsigned char status_byte;
  3621. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  3622. status_byte = RD_HARPOON(p_port + hp_gp_reg_0);
  3623. FPT_sccbMgrTbl[p_card][currSCCB->TargID].TarLUN_CA = 0;
  3624. if (status_byte != SSGOOD) {
  3625. if (status_byte == SSQ_FULL) {
  3626. if (((FPT_BL_Card[p_card].globalFlags & F_CONLUN_IO) &&
  3627. ((FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3628. TarStatus & TAR_TAG_Q_MASK) != TAG_Q_TRYING))) {
  3629. FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3630. TarLUNBusy[currSCCB->Lun] = 1;
  3631. if (FPT_BL_Card[p_card].discQCount != 0)
  3632. FPT_BL_Card[p_card].discQCount--;
  3633. FPT_BL_Card[p_card].
  3634. discQ_Tbl[FPT_sccbMgrTbl[p_card]
  3635. [currSCCB->TargID].
  3636. LunDiscQ_Idx[currSCCB->Lun]] =
  3637. NULL;
  3638. } else {
  3639. FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3640. TarLUNBusy[0] = 1;
  3641. if (currSCCB->Sccb_tag) {
  3642. if (FPT_BL_Card[p_card].discQCount != 0)
  3643. FPT_BL_Card[p_card].
  3644. discQCount--;
  3645. FPT_BL_Card[p_card].discQ_Tbl[currSCCB->
  3646. Sccb_tag]
  3647. = NULL;
  3648. } else {
  3649. if (FPT_BL_Card[p_card].discQCount != 0)
  3650. FPT_BL_Card[p_card].
  3651. discQCount--;
  3652. FPT_BL_Card[p_card].
  3653. discQ_Tbl[FPT_sccbMgrTbl[p_card]
  3654. [currSCCB->TargID].
  3655. LunDiscQ_Idx[0]] = NULL;
  3656. }
  3657. }
  3658. currSCCB->Sccb_MGRFlags |= F_STATUSLOADED;
  3659. FPT_queueSelectFail(&FPT_BL_Card[p_card], p_card);
  3660. return;
  3661. }
  3662. if (currSCCB->Sccb_scsistat == SELECT_SN_ST) {
  3663. FPT_sccbMgrTbl[p_card][currSCCB->TargID].TarStatus |=
  3664. (unsigned char)SYNC_SUPPORTED;
  3665. FPT_sccbMgrTbl[p_card][currSCCB->TargID].TarEEValue &=
  3666. ~EE_SYNC_MASK;
  3667. FPT_BL_Card[p_card].globalFlags |= F_NEW_SCCB_CMD;
  3668. if (((FPT_BL_Card[p_card].globalFlags & F_CONLUN_IO) &&
  3669. ((FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3670. TarStatus & TAR_TAG_Q_MASK) != TAG_Q_TRYING))) {
  3671. FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3672. TarLUNBusy[currSCCB->Lun] = 1;
  3673. if (FPT_BL_Card[p_card].discQCount != 0)
  3674. FPT_BL_Card[p_card].discQCount--;
  3675. FPT_BL_Card[p_card].
  3676. discQ_Tbl[FPT_sccbMgrTbl[p_card]
  3677. [currSCCB->TargID].
  3678. LunDiscQ_Idx[currSCCB->Lun]] =
  3679. NULL;
  3680. } else {
  3681. FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3682. TarLUNBusy[0] = 1;
  3683. if (currSCCB->Sccb_tag) {
  3684. if (FPT_BL_Card[p_card].discQCount != 0)
  3685. FPT_BL_Card[p_card].
  3686. discQCount--;
  3687. FPT_BL_Card[p_card].discQ_Tbl[currSCCB->
  3688. Sccb_tag]
  3689. = NULL;
  3690. } else {
  3691. if (FPT_BL_Card[p_card].discQCount != 0)
  3692. FPT_BL_Card[p_card].
  3693. discQCount--;
  3694. FPT_BL_Card[p_card].
  3695. discQ_Tbl[FPT_sccbMgrTbl[p_card]
  3696. [currSCCB->TargID].
  3697. LunDiscQ_Idx[0]] = NULL;
  3698. }
  3699. }
  3700. return;
  3701. }
  3702. if (currSCCB->Sccb_scsistat == SELECT_WN_ST) {
  3703. FPT_sccbMgrTbl[p_card][currSCCB->TargID].TarStatus =
  3704. (FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3705. TarStatus & ~WIDE_ENABLED) | WIDE_NEGOCIATED;
  3706. FPT_sccbMgrTbl[p_card][currSCCB->TargID].TarEEValue &=
  3707. ~EE_WIDE_SCSI;
  3708. FPT_BL_Card[p_card].globalFlags |= F_NEW_SCCB_CMD;
  3709. if (((FPT_BL_Card[p_card].globalFlags & F_CONLUN_IO) &&
  3710. ((FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3711. TarStatus & TAR_TAG_Q_MASK) != TAG_Q_TRYING))) {
  3712. FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3713. TarLUNBusy[currSCCB->Lun] = 1;
  3714. if (FPT_BL_Card[p_card].discQCount != 0)
  3715. FPT_BL_Card[p_card].discQCount--;
  3716. FPT_BL_Card[p_card].
  3717. discQ_Tbl[FPT_sccbMgrTbl[p_card]
  3718. [currSCCB->TargID].
  3719. LunDiscQ_Idx[currSCCB->Lun]] =
  3720. NULL;
  3721. } else {
  3722. FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3723. TarLUNBusy[0] = 1;
  3724. if (currSCCB->Sccb_tag) {
  3725. if (FPT_BL_Card[p_card].discQCount != 0)
  3726. FPT_BL_Card[p_card].
  3727. discQCount--;
  3728. FPT_BL_Card[p_card].discQ_Tbl[currSCCB->
  3729. Sccb_tag]
  3730. = NULL;
  3731. } else {
  3732. if (FPT_BL_Card[p_card].discQCount != 0)
  3733. FPT_BL_Card[p_card].
  3734. discQCount--;
  3735. FPT_BL_Card[p_card].
  3736. discQ_Tbl[FPT_sccbMgrTbl[p_card]
  3737. [currSCCB->TargID].
  3738. LunDiscQ_Idx[0]] = NULL;
  3739. }
  3740. }
  3741. return;
  3742. }
  3743. if (status_byte == SSCHECK) {
  3744. if (FPT_BL_Card[p_card].globalFlags & F_DO_RENEGO) {
  3745. if (FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3746. TarEEValue & EE_SYNC_MASK) {
  3747. FPT_sccbMgrTbl[p_card][currSCCB->
  3748. TargID].
  3749. TarStatus &= ~TAR_SYNC_MASK;
  3750. }
  3751. if (FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3752. TarEEValue & EE_WIDE_SCSI) {
  3753. FPT_sccbMgrTbl[p_card][currSCCB->
  3754. TargID].
  3755. TarStatus &= ~TAR_WIDE_MASK;
  3756. }
  3757. }
  3758. }
  3759. if (!(currSCCB->Sccb_XferState & F_AUTO_SENSE)) {
  3760. currSCCB->SccbStatus = SCCB_ERROR;
  3761. currSCCB->TargetStatus = status_byte;
  3762. if (status_byte == SSCHECK) {
  3763. FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3764. TarLUN_CA = 1;
  3765. if (currSCCB->RequestSenseLength !=
  3766. NO_AUTO_REQUEST_SENSE) {
  3767. if (currSCCB->RequestSenseLength == 0)
  3768. currSCCB->RequestSenseLength =
  3769. 14;
  3770. FPT_ssenss(&FPT_BL_Card[p_card]);
  3771. FPT_BL_Card[p_card].globalFlags |=
  3772. F_NEW_SCCB_CMD;
  3773. if (((FPT_BL_Card[p_card].
  3774. globalFlags & F_CONLUN_IO)
  3775. &&
  3776. ((FPT_sccbMgrTbl[p_card]
  3777. [currSCCB->TargID].
  3778. TarStatus & TAR_TAG_Q_MASK) !=
  3779. TAG_Q_TRYING))) {
  3780. FPT_sccbMgrTbl[p_card]
  3781. [currSCCB->TargID].
  3782. TarLUNBusy[currSCCB->Lun] =
  3783. 1;
  3784. if (FPT_BL_Card[p_card].
  3785. discQCount != 0)
  3786. FPT_BL_Card[p_card].
  3787. discQCount--;
  3788. FPT_BL_Card[p_card].
  3789. discQ_Tbl[FPT_sccbMgrTbl
  3790. [p_card]
  3791. [currSCCB->
  3792. TargID].
  3793. LunDiscQ_Idx
  3794. [currSCCB->Lun]] =
  3795. NULL;
  3796. } else {
  3797. FPT_sccbMgrTbl[p_card]
  3798. [currSCCB->TargID].
  3799. TarLUNBusy[0] = 1;
  3800. if (currSCCB->Sccb_tag) {
  3801. if (FPT_BL_Card[p_card].
  3802. discQCount != 0)
  3803. FPT_BL_Card
  3804. [p_card].
  3805. discQCount--;
  3806. FPT_BL_Card[p_card].
  3807. discQ_Tbl[currSCCB->
  3808. Sccb_tag]
  3809. = NULL;
  3810. } else {
  3811. if (FPT_BL_Card[p_card].
  3812. discQCount != 0)
  3813. FPT_BL_Card
  3814. [p_card].
  3815. discQCount--;
  3816. FPT_BL_Card[p_card].
  3817. discQ_Tbl
  3818. [FPT_sccbMgrTbl
  3819. [p_card][currSCCB->
  3820. TargID].
  3821. LunDiscQ_Idx[0]] =
  3822. NULL;
  3823. }
  3824. }
  3825. return;
  3826. }
  3827. }
  3828. }
  3829. }
  3830. if ((FPT_BL_Card[p_card].globalFlags & F_CONLUN_IO) &&
  3831. ((FPT_sccbMgrTbl[p_card][currSCCB->TargID].
  3832. TarStatus & TAR_TAG_Q_MASK) != TAG_Q_TRYING))
  3833. FPT_sccbMgrTbl[p_card][currSCCB->TargID].TarLUNBusy[currSCCB->
  3834. Lun] = 0;
  3835. else
  3836. FPT_sccbMgrTbl[p_card][currSCCB->TargID].TarLUNBusy[0] = 0;
  3837. FPT_queueCmdComplete(&FPT_BL_Card[p_card], currSCCB, p_card);
  3838. }
  3839. #define SHORT_WAIT 0x0000000F
  3840. #define LONG_WAIT 0x0000FFFFL
  3841. /*---------------------------------------------------------------------
  3842. *
  3843. * Function: Data Transfer Processor
  3844. *
  3845. * Description: This routine performs two tasks.
  3846. * (1) Start data transfer by calling HOST_DATA_XFER_START
  3847. * function. Once data transfer is started, (2) Depends
  3848. * on the type of data transfer mode Scatter/Gather mode
  3849. * or NON Scatter/Gather mode. In NON Scatter/Gather mode,
  3850. * this routine checks Sccb_MGRFlag (F_HOST_XFER_ACT bit) for
  3851. * data transfer done. In Scatter/Gather mode, this routine
  3852. * checks bus master command complete and dual rank busy
  3853. * bit to keep chaining SC transfer command. Similarly,
  3854. * in Scatter/Gather mode, it checks Sccb_MGRFlag
  3855. * (F_HOST_XFER_ACT bit) for data transfer done.
  3856. *
  3857. *---------------------------------------------------------------------*/
  3858. static void FPT_dataXferProcessor(u32 port, struct sccb_card *pCurrCard)
  3859. {
  3860. struct sccb *currSCCB;
  3861. currSCCB = pCurrCard->currentSCCB;
  3862. if (currSCCB->Sccb_XferState & F_SG_XFER) {
  3863. if (pCurrCard->globalFlags & F_HOST_XFER_ACT)
  3864. {
  3865. currSCCB->Sccb_sgseg += (unsigned char)SG_BUF_CNT;
  3866. currSCCB->Sccb_SGoffset = 0x00;
  3867. }
  3868. pCurrCard->globalFlags |= F_HOST_XFER_ACT;
  3869. FPT_busMstrSGDataXferStart(port, currSCCB);
  3870. }
  3871. else {
  3872. if (!(pCurrCard->globalFlags & F_HOST_XFER_ACT)) {
  3873. pCurrCard->globalFlags |= F_HOST_XFER_ACT;
  3874. FPT_busMstrDataXferStart(port, currSCCB);
  3875. }
  3876. }
  3877. }
  3878. /*---------------------------------------------------------------------
  3879. *
  3880. * Function: BusMaster Scatter Gather Data Transfer Start
  3881. *
  3882. * Description:
  3883. *
  3884. *---------------------------------------------------------------------*/
  3885. static void FPT_busMstrSGDataXferStart(u32 p_port, struct sccb *pcurrSCCB)
  3886. {
  3887. u32 count, addr, tmpSGCnt;
  3888. unsigned int sg_index;
  3889. unsigned char sg_count, i;
  3890. u32 reg_offset;
  3891. struct blogic_sg_seg *segp;
  3892. if (pcurrSCCB->Sccb_XferState & F_HOST_XFER_DIR)
  3893. count = ((u32)HOST_RD_CMD) << 24;
  3894. else
  3895. count = ((u32)HOST_WRT_CMD) << 24;
  3896. sg_count = 0;
  3897. tmpSGCnt = 0;
  3898. sg_index = pcurrSCCB->Sccb_sgseg;
  3899. reg_offset = hp_aramBase;
  3900. i = (unsigned char)(RD_HARPOON(p_port + hp_page_ctrl) &
  3901. ~(SGRAM_ARAM | SCATTER_EN));
  3902. WR_HARPOON(p_port + hp_page_ctrl, i);
  3903. while ((sg_count < (unsigned char)SG_BUF_CNT) &&
  3904. ((sg_index * (unsigned int)SG_ELEMENT_SIZE) <
  3905. pcurrSCCB->DataLength)) {
  3906. segp = (struct blogic_sg_seg *)(pcurrSCCB->DataPointer) +
  3907. sg_index;
  3908. tmpSGCnt += segp->segbytes;
  3909. count |= segp->segbytes;
  3910. addr = segp->segdata;
  3911. if ((!sg_count) && (pcurrSCCB->Sccb_SGoffset)) {
  3912. addr +=
  3913. ((count & 0x00FFFFFFL) - pcurrSCCB->Sccb_SGoffset);
  3914. count =
  3915. (count & 0xFF000000L) | pcurrSCCB->Sccb_SGoffset;
  3916. tmpSGCnt = count & 0x00FFFFFFL;
  3917. }
  3918. WR_HARP32(p_port, reg_offset, addr);
  3919. reg_offset += 4;
  3920. WR_HARP32(p_port, reg_offset, count);
  3921. reg_offset += 4;
  3922. count &= 0xFF000000L;
  3923. sg_index++;
  3924. sg_count++;
  3925. } /*End While */
  3926. pcurrSCCB->Sccb_XferCnt = tmpSGCnt;
  3927. WR_HARPOON(p_port + hp_sg_addr, (sg_count << 4));
  3928. if (pcurrSCCB->Sccb_XferState & F_HOST_XFER_DIR) {
  3929. WR_HARP32(p_port, hp_xfercnt_0, tmpSGCnt);
  3930. WR_HARPOON(p_port + hp_portctrl_0,
  3931. (DMA_PORT | SCSI_PORT | SCSI_INBIT));
  3932. WR_HARPOON(p_port + hp_scsisig, S_DATAI_PH);
  3933. }
  3934. else {
  3935. if ((!(RD_HARPOON(p_port + hp_synctarg_0) & NARROW_SCSI)) &&
  3936. (tmpSGCnt & 0x000000001)) {
  3937. pcurrSCCB->Sccb_XferState |= F_ODD_BALL_CNT;
  3938. tmpSGCnt--;
  3939. }
  3940. WR_HARP32(p_port, hp_xfercnt_0, tmpSGCnt);
  3941. WR_HARPOON(p_port + hp_portctrl_0,
  3942. (SCSI_PORT | DMA_PORT | DMA_RD));
  3943. WR_HARPOON(p_port + hp_scsisig, S_DATAO_PH);
  3944. }
  3945. WR_HARPOON(p_port + hp_page_ctrl, (unsigned char)(i | SCATTER_EN));
  3946. }
  3947. /*---------------------------------------------------------------------
  3948. *
  3949. * Function: BusMaster Data Transfer Start
  3950. *
  3951. * Description:
  3952. *
  3953. *---------------------------------------------------------------------*/
  3954. static void FPT_busMstrDataXferStart(u32 p_port, struct sccb *pcurrSCCB)
  3955. {
  3956. u32 addr, count;
  3957. if (!(pcurrSCCB->Sccb_XferState & F_AUTO_SENSE)) {
  3958. count = pcurrSCCB->Sccb_XferCnt;
  3959. addr = (u32)(unsigned long)pcurrSCCB->DataPointer + pcurrSCCB->Sccb_ATC;
  3960. }
  3961. else {
  3962. addr = pcurrSCCB->SensePointer;
  3963. count = pcurrSCCB->RequestSenseLength;
  3964. }
  3965. HP_SETUP_ADDR_CNT(p_port, addr, count);
  3966. if (pcurrSCCB->Sccb_XferState & F_HOST_XFER_DIR) {
  3967. WR_HARPOON(p_port + hp_portctrl_0,
  3968. (DMA_PORT | SCSI_PORT | SCSI_INBIT));
  3969. WR_HARPOON(p_port + hp_scsisig, S_DATAI_PH);
  3970. WR_HARPOON(p_port + hp_xfer_cmd,
  3971. (XFER_DMA_HOST | XFER_HOST_AUTO | XFER_DMA_8BIT));
  3972. }
  3973. else {
  3974. WR_HARPOON(p_port + hp_portctrl_0,
  3975. (SCSI_PORT | DMA_PORT | DMA_RD));
  3976. WR_HARPOON(p_port + hp_scsisig, S_DATAO_PH);
  3977. WR_HARPOON(p_port + hp_xfer_cmd,
  3978. (XFER_HOST_DMA | XFER_HOST_AUTO | XFER_DMA_8BIT));
  3979. }
  3980. }
  3981. /*---------------------------------------------------------------------
  3982. *
  3983. * Function: BusMaster Timeout Handler
  3984. *
  3985. * Description: This function is called after a bus master command busy time
  3986. * out is detected. This routines issue halt state machine
  3987. * with a software time out for command busy. If command busy
  3988. * is still asserted at the end of the time out, it issues
  3989. * hard abort with another software time out. It hard abort
  3990. * command busy is also time out, it'll just give up.
  3991. *
  3992. *---------------------------------------------------------------------*/
  3993. static unsigned char FPT_busMstrTimeOut(u32 p_port)
  3994. {
  3995. unsigned long timeout;
  3996. timeout = LONG_WAIT;
  3997. WR_HARPOON(p_port + hp_sys_ctrl, HALT_MACH);
  3998. while ((!(RD_HARPOON(p_port + hp_ext_status) & CMD_ABORTED))
  3999. && timeout--) {
  4000. }
  4001. if (RD_HARPOON(p_port + hp_ext_status) & BM_CMD_BUSY) {
  4002. WR_HARPOON(p_port + hp_sys_ctrl, HARD_ABORT);
  4003. timeout = LONG_WAIT;
  4004. while ((RD_HARPOON(p_port + hp_ext_status) & BM_CMD_BUSY)
  4005. && timeout--) {
  4006. }
  4007. }
  4008. RD_HARPOON(p_port + hp_int_status); /*Clear command complete */
  4009. if (RD_HARPOON(p_port + hp_ext_status) & BM_CMD_BUSY) {
  4010. return 1;
  4011. }
  4012. else {
  4013. return 0;
  4014. }
  4015. }
  4016. /*---------------------------------------------------------------------
  4017. *
  4018. * Function: Host Data Transfer Abort
  4019. *
  4020. * Description: Abort any in progress transfer.
  4021. *
  4022. *---------------------------------------------------------------------*/
  4023. static void FPT_hostDataXferAbort(u32 port, unsigned char p_card,
  4024. struct sccb *pCurrSCCB)
  4025. {
  4026. unsigned long timeout;
  4027. unsigned long remain_cnt;
  4028. u32 sg_ptr;
  4029. struct blogic_sg_seg *segp;
  4030. FPT_BL_Card[p_card].globalFlags &= ~F_HOST_XFER_ACT;
  4031. if (pCurrSCCB->Sccb_XferState & F_AUTO_SENSE) {
  4032. if (!(RD_HARPOON(port + hp_int_status) & INT_CMD_COMPL)) {
  4033. WR_HARPOON(port + hp_bm_ctrl,
  4034. (RD_HARPOON(port + hp_bm_ctrl) |
  4035. FLUSH_XFER_CNTR));
  4036. timeout = LONG_WAIT;
  4037. while ((RD_HARPOON(port + hp_ext_status) & BM_CMD_BUSY)
  4038. && timeout--) {
  4039. }
  4040. WR_HARPOON(port + hp_bm_ctrl,
  4041. (RD_HARPOON(port + hp_bm_ctrl) &
  4042. ~FLUSH_XFER_CNTR));
  4043. if (RD_HARPOON(port + hp_ext_status) & BM_CMD_BUSY) {
  4044. if (FPT_busMstrTimeOut(port)) {
  4045. if (pCurrSCCB->HostStatus == 0x00)
  4046. pCurrSCCB->HostStatus =
  4047. SCCB_BM_ERR;
  4048. }
  4049. if (RD_HARPOON(port + hp_int_status) &
  4050. INT_EXT_STATUS)
  4051. if (RD_HARPOON(port + hp_ext_status) &
  4052. BAD_EXT_STATUS)
  4053. if (pCurrSCCB->HostStatus ==
  4054. 0x00)
  4055. {
  4056. pCurrSCCB->HostStatus =
  4057. SCCB_BM_ERR;
  4058. }
  4059. }
  4060. }
  4061. }
  4062. else if (pCurrSCCB->Sccb_XferCnt) {
  4063. if (pCurrSCCB->Sccb_XferState & F_SG_XFER) {
  4064. WR_HARPOON(port + hp_page_ctrl,
  4065. (RD_HARPOON(port + hp_page_ctrl) &
  4066. ~SCATTER_EN));
  4067. WR_HARPOON(port + hp_sg_addr, 0x00);
  4068. sg_ptr = pCurrSCCB->Sccb_sgseg + SG_BUF_CNT;
  4069. if (sg_ptr >
  4070. (unsigned int)(pCurrSCCB->DataLength /
  4071. SG_ELEMENT_SIZE)) {
  4072. sg_ptr = (u32)(pCurrSCCB->DataLength /
  4073. SG_ELEMENT_SIZE);
  4074. }
  4075. remain_cnt = pCurrSCCB->Sccb_XferCnt;
  4076. while (remain_cnt < 0x01000000L) {
  4077. sg_ptr--;
  4078. segp = (struct blogic_sg_seg *)(pCurrSCCB->
  4079. DataPointer) + (sg_ptr * 2);
  4080. if (remain_cnt > (unsigned long)segp->segbytes)
  4081. remain_cnt -=
  4082. (unsigned long)segp->segbytes;
  4083. else
  4084. break;
  4085. }
  4086. if (remain_cnt < 0x01000000L) {
  4087. pCurrSCCB->Sccb_SGoffset = remain_cnt;
  4088. pCurrSCCB->Sccb_sgseg = (unsigned short)sg_ptr;
  4089. if ((unsigned long)(sg_ptr * SG_ELEMENT_SIZE) ==
  4090. pCurrSCCB->DataLength && (remain_cnt == 0))
  4091. pCurrSCCB->Sccb_XferState |=
  4092. F_ALL_XFERRED;
  4093. }
  4094. else {
  4095. if (pCurrSCCB->HostStatus == 0x00) {
  4096. pCurrSCCB->HostStatus =
  4097. SCCB_GROSS_FW_ERR;
  4098. }
  4099. }
  4100. }
  4101. if (!(pCurrSCCB->Sccb_XferState & F_HOST_XFER_DIR)) {
  4102. if (RD_HARPOON(port + hp_ext_status) & BM_CMD_BUSY) {
  4103. FPT_busMstrTimeOut(port);
  4104. }
  4105. else {
  4106. if (RD_HARPOON(port + hp_int_status) &
  4107. INT_EXT_STATUS) {
  4108. if (RD_HARPOON(port + hp_ext_status) &
  4109. BAD_EXT_STATUS) {
  4110. if (pCurrSCCB->HostStatus ==
  4111. 0x00) {
  4112. pCurrSCCB->HostStatus =
  4113. SCCB_BM_ERR;
  4114. }
  4115. }
  4116. }
  4117. }
  4118. }
  4119. else {
  4120. if ((RD_HARPOON(port + hp_fifo_cnt)) >= BM_THRESHOLD) {
  4121. timeout = SHORT_WAIT;
  4122. while ((RD_HARPOON(port + hp_ext_status) &
  4123. BM_CMD_BUSY)
  4124. && ((RD_HARPOON(port + hp_fifo_cnt)) >=
  4125. BM_THRESHOLD) && timeout--) {
  4126. }
  4127. }
  4128. if (RD_HARPOON(port + hp_ext_status) & BM_CMD_BUSY) {
  4129. WR_HARPOON(port + hp_bm_ctrl,
  4130. (RD_HARPOON(port + hp_bm_ctrl) |
  4131. FLUSH_XFER_CNTR));
  4132. timeout = LONG_WAIT;
  4133. while ((RD_HARPOON(port + hp_ext_status) &
  4134. BM_CMD_BUSY) && timeout--) {
  4135. }
  4136. WR_HARPOON(port + hp_bm_ctrl,
  4137. (RD_HARPOON(port + hp_bm_ctrl) &
  4138. ~FLUSH_XFER_CNTR));
  4139. if (RD_HARPOON(port + hp_ext_status) &
  4140. BM_CMD_BUSY) {
  4141. if (pCurrSCCB->HostStatus == 0x00) {
  4142. pCurrSCCB->HostStatus =
  4143. SCCB_BM_ERR;
  4144. }
  4145. FPT_busMstrTimeOut(port);
  4146. }
  4147. }
  4148. if (RD_HARPOON(port + hp_int_status) & INT_EXT_STATUS) {
  4149. if (RD_HARPOON(port + hp_ext_status) &
  4150. BAD_EXT_STATUS) {
  4151. if (pCurrSCCB->HostStatus == 0x00) {
  4152. pCurrSCCB->HostStatus =
  4153. SCCB_BM_ERR;
  4154. }
  4155. }
  4156. }
  4157. }
  4158. }
  4159. else {
  4160. if (RD_HARPOON(port + hp_ext_status) & BM_CMD_BUSY) {
  4161. timeout = LONG_WAIT;
  4162. while ((RD_HARPOON(port + hp_ext_status) & BM_CMD_BUSY)
  4163. && timeout--) {
  4164. }
  4165. if (RD_HARPOON(port + hp_ext_status) & BM_CMD_BUSY) {
  4166. if (pCurrSCCB->HostStatus == 0x00) {
  4167. pCurrSCCB->HostStatus = SCCB_BM_ERR;
  4168. }
  4169. FPT_busMstrTimeOut(port);
  4170. }
  4171. }
  4172. if (RD_HARPOON(port + hp_int_status) & INT_EXT_STATUS) {
  4173. if (RD_HARPOON(port + hp_ext_status) & BAD_EXT_STATUS) {
  4174. if (pCurrSCCB->HostStatus == 0x00) {
  4175. pCurrSCCB->HostStatus = SCCB_BM_ERR;
  4176. }
  4177. }
  4178. }
  4179. if (pCurrSCCB->Sccb_XferState & F_SG_XFER) {
  4180. WR_HARPOON(port + hp_page_ctrl,
  4181. (RD_HARPOON(port + hp_page_ctrl) &
  4182. ~SCATTER_EN));
  4183. WR_HARPOON(port + hp_sg_addr, 0x00);
  4184. pCurrSCCB->Sccb_sgseg += SG_BUF_CNT;
  4185. pCurrSCCB->Sccb_SGoffset = 0x00;
  4186. if ((u32)(pCurrSCCB->Sccb_sgseg * SG_ELEMENT_SIZE) >=
  4187. pCurrSCCB->DataLength) {
  4188. pCurrSCCB->Sccb_XferState |= F_ALL_XFERRED;
  4189. pCurrSCCB->Sccb_sgseg =
  4190. (unsigned short)(pCurrSCCB->DataLength /
  4191. SG_ELEMENT_SIZE);
  4192. }
  4193. }
  4194. else {
  4195. if (!(pCurrSCCB->Sccb_XferState & F_AUTO_SENSE))
  4196. pCurrSCCB->Sccb_XferState |= F_ALL_XFERRED;
  4197. }
  4198. }
  4199. WR_HARPOON(port + hp_int_mask, (INT_CMD_COMPL | SCSI_INTERRUPT));
  4200. }
  4201. /*---------------------------------------------------------------------
  4202. *
  4203. * Function: Host Data Transfer Restart
  4204. *
  4205. * Description: Reset the available count due to a restore data
  4206. * pointers message.
  4207. *
  4208. *---------------------------------------------------------------------*/
  4209. static void FPT_hostDataXferRestart(struct sccb *currSCCB)
  4210. {
  4211. unsigned long data_count;
  4212. unsigned int sg_index;
  4213. struct blogic_sg_seg *segp;
  4214. if (currSCCB->Sccb_XferState & F_SG_XFER) {
  4215. currSCCB->Sccb_XferCnt = 0;
  4216. sg_index = 0xffff; /*Index by long words into sg list. */
  4217. data_count = 0; /*Running count of SG xfer counts. */
  4218. while (data_count < currSCCB->Sccb_ATC) {
  4219. sg_index++;
  4220. segp = (struct blogic_sg_seg *)(currSCCB->DataPointer) +
  4221. (sg_index * 2);
  4222. data_count += segp->segbytes;
  4223. }
  4224. if (data_count == currSCCB->Sccb_ATC) {
  4225. currSCCB->Sccb_SGoffset = 0;
  4226. sg_index++;
  4227. }
  4228. else {
  4229. currSCCB->Sccb_SGoffset =
  4230. data_count - currSCCB->Sccb_ATC;
  4231. }
  4232. currSCCB->Sccb_sgseg = (unsigned short)sg_index;
  4233. }
  4234. else {
  4235. currSCCB->Sccb_XferCnt =
  4236. currSCCB->DataLength - currSCCB->Sccb_ATC;
  4237. }
  4238. }
  4239. /*---------------------------------------------------------------------
  4240. *
  4241. * Function: FPT_scini
  4242. *
  4243. * Description: Setup all data structures necessary for SCAM selection.
  4244. *
  4245. *---------------------------------------------------------------------*/
  4246. static void FPT_scini(unsigned char p_card, unsigned char p_our_id,
  4247. unsigned char p_power_up)
  4248. {
  4249. unsigned char loser, assigned_id;
  4250. u32 p_port;
  4251. unsigned char i, k, ScamFlg;
  4252. struct sccb_card *currCard;
  4253. struct nvram_info *pCurrNvRam;
  4254. currCard = &FPT_BL_Card[p_card];
  4255. p_port = currCard->ioPort;
  4256. pCurrNvRam = currCard->pNvRamInfo;
  4257. if (pCurrNvRam) {
  4258. ScamFlg = pCurrNvRam->niScamConf;
  4259. i = pCurrNvRam->niSysConf;
  4260. } else {
  4261. ScamFlg =
  4262. (unsigned char)FPT_utilEERead(p_port, SCAM_CONFIG / 2);
  4263. i = (unsigned
  4264. char)(FPT_utilEERead(p_port, (SYSTEM_CONFIG / 2)));
  4265. }
  4266. if (!(i & 0x02)) /* check if reset bus in AutoSCSI parameter set */
  4267. return;
  4268. FPT_inisci(p_card, p_port, p_our_id);
  4269. /* Force to wait 1 sec after SCSI bus reset. Some SCAM device FW
  4270. too slow to return to SCAM selection */
  4271. /* if (p_power_up)
  4272. FPT_Wait1Second(p_port);
  4273. else
  4274. FPT_Wait(p_port, TO_250ms); */
  4275. FPT_Wait1Second(p_port);
  4276. if ((ScamFlg & SCAM_ENABLED) && (ScamFlg & SCAM_LEVEL2)) {
  4277. while (!(FPT_scarb(p_port, INIT_SELTD))) {
  4278. }
  4279. FPT_scsel(p_port);
  4280. do {
  4281. FPT_scxferc(p_port, SYNC_PTRN);
  4282. FPT_scxferc(p_port, DOM_MSTR);
  4283. loser =
  4284. FPT_scsendi(p_port,
  4285. &FPT_scamInfo[p_our_id].id_string[0]);
  4286. } while (loser == 0xFF);
  4287. FPT_scbusf(p_port);
  4288. if ((p_power_up) && (!loser)) {
  4289. FPT_sresb(p_port, p_card);
  4290. FPT_Wait(p_port, TO_250ms);
  4291. while (!(FPT_scarb(p_port, INIT_SELTD))) {
  4292. }
  4293. FPT_scsel(p_port);
  4294. do {
  4295. FPT_scxferc(p_port, SYNC_PTRN);
  4296. FPT_scxferc(p_port, DOM_MSTR);
  4297. loser =
  4298. FPT_scsendi(p_port,
  4299. &FPT_scamInfo[p_our_id].
  4300. id_string[0]);
  4301. } while (loser == 0xFF);
  4302. FPT_scbusf(p_port);
  4303. }
  4304. }
  4305. else {
  4306. loser = 0;
  4307. }
  4308. if (!loser) {
  4309. FPT_scamInfo[p_our_id].state = ID_ASSIGNED;
  4310. if (ScamFlg & SCAM_ENABLED) {
  4311. for (i = 0; i < MAX_SCSI_TAR; i++) {
  4312. if ((FPT_scamInfo[i].state == ID_UNASSIGNED) ||
  4313. (FPT_scamInfo[i].state == ID_UNUSED)) {
  4314. if (FPT_scsell(p_port, i)) {
  4315. FPT_scamInfo[i].state = LEGACY;
  4316. if ((FPT_scamInfo[i].
  4317. id_string[0] != 0xFF)
  4318. || (FPT_scamInfo[i].
  4319. id_string[1] != 0xFA)) {
  4320. FPT_scamInfo[i].
  4321. id_string[0] = 0xFF;
  4322. FPT_scamInfo[i].
  4323. id_string[1] = 0xFA;
  4324. if (pCurrNvRam == NULL)
  4325. currCard->
  4326. globalFlags
  4327. |=
  4328. F_UPDATE_EEPROM;
  4329. }
  4330. }
  4331. }
  4332. }
  4333. FPT_sresb(p_port, p_card);
  4334. FPT_Wait1Second(p_port);
  4335. while (!(FPT_scarb(p_port, INIT_SELTD))) {
  4336. }
  4337. FPT_scsel(p_port);
  4338. FPT_scasid(p_card, p_port);
  4339. }
  4340. }
  4341. else if ((loser) && (ScamFlg & SCAM_ENABLED)) {
  4342. FPT_scamInfo[p_our_id].id_string[0] = SLV_TYPE_CODE0;
  4343. assigned_id = 0;
  4344. FPT_scwtsel(p_port);
  4345. do {
  4346. while (FPT_scxferc(p_port, 0x00) != SYNC_PTRN) {
  4347. }
  4348. i = FPT_scxferc(p_port, 0x00);
  4349. if (i == ASSIGN_ID) {
  4350. if (!
  4351. (FPT_scsendi
  4352. (p_port,
  4353. &FPT_scamInfo[p_our_id].id_string[0]))) {
  4354. i = FPT_scxferc(p_port, 0x00);
  4355. if (FPT_scvalq(i)) {
  4356. k = FPT_scxferc(p_port, 0x00);
  4357. if (FPT_scvalq(k)) {
  4358. currCard->ourId =
  4359. ((unsigned char)(i
  4360. <<
  4361. 3)
  4362. +
  4363. (k &
  4364. (unsigned char)7))
  4365. & (unsigned char)
  4366. 0x3F;
  4367. FPT_inisci(p_card,
  4368. p_port,
  4369. p_our_id);
  4370. FPT_scamInfo[currCard->
  4371. ourId].
  4372. state = ID_ASSIGNED;
  4373. FPT_scamInfo[currCard->
  4374. ourId].
  4375. id_string[0]
  4376. = SLV_TYPE_CODE0;
  4377. assigned_id = 1;
  4378. }
  4379. }
  4380. }
  4381. }
  4382. else if (i == SET_P_FLAG) {
  4383. if (!(FPT_scsendi(p_port,
  4384. &FPT_scamInfo[p_our_id].
  4385. id_string[0])))
  4386. FPT_scamInfo[p_our_id].id_string[0] |=
  4387. 0x80;
  4388. }
  4389. } while (!assigned_id);
  4390. while (FPT_scxferc(p_port, 0x00) != CFG_CMPLT) {
  4391. }
  4392. }
  4393. if (ScamFlg & SCAM_ENABLED) {
  4394. FPT_scbusf(p_port);
  4395. if (currCard->globalFlags & F_UPDATE_EEPROM) {
  4396. FPT_scsavdi(p_card, p_port);
  4397. currCard->globalFlags &= ~F_UPDATE_EEPROM;
  4398. }
  4399. }
  4400. /*
  4401. for (i=0,k=0; i < MAX_SCSI_TAR; i++)
  4402. {
  4403. if ((FPT_scamInfo[i].state == ID_ASSIGNED) ||
  4404. (FPT_scamInfo[i].state == LEGACY))
  4405. k++;
  4406. }
  4407. if (k==2)
  4408. currCard->globalFlags |= F_SINGLE_DEVICE;
  4409. else
  4410. currCard->globalFlags &= ~F_SINGLE_DEVICE;
  4411. */
  4412. }
  4413. /*---------------------------------------------------------------------
  4414. *
  4415. * Function: FPT_scarb
  4416. *
  4417. * Description: Gain control of the bus and wait SCAM select time (250ms)
  4418. *
  4419. *---------------------------------------------------------------------*/
  4420. static int FPT_scarb(u32 p_port, unsigned char p_sel_type)
  4421. {
  4422. if (p_sel_type == INIT_SELTD) {
  4423. while (RD_HARPOON(p_port + hp_scsisig) & (SCSI_SEL | SCSI_BSY)) {
  4424. }
  4425. if (RD_HARPOON(p_port + hp_scsisig) & SCSI_SEL)
  4426. return 0;
  4427. if (RD_HARPOON(p_port + hp_scsidata_0) != 00)
  4428. return 0;
  4429. WR_HARPOON(p_port + hp_scsisig,
  4430. (RD_HARPOON(p_port + hp_scsisig) | SCSI_BSY));
  4431. if (RD_HARPOON(p_port + hp_scsisig) & SCSI_SEL) {
  4432. WR_HARPOON(p_port + hp_scsisig,
  4433. (RD_HARPOON(p_port + hp_scsisig) &
  4434. ~SCSI_BSY));
  4435. return 0;
  4436. }
  4437. WR_HARPOON(p_port + hp_scsisig,
  4438. (RD_HARPOON(p_port + hp_scsisig) | SCSI_SEL));
  4439. if (RD_HARPOON(p_port + hp_scsidata_0) != 00) {
  4440. WR_HARPOON(p_port + hp_scsisig,
  4441. (RD_HARPOON(p_port + hp_scsisig) &
  4442. ~(SCSI_BSY | SCSI_SEL)));
  4443. return 0;
  4444. }
  4445. }
  4446. WR_HARPOON(p_port + hp_clkctrl_0, (RD_HARPOON(p_port + hp_clkctrl_0)
  4447. & ~ACTdeassert));
  4448. WR_HARPOON(p_port + hp_scsireset, SCAM_EN);
  4449. WR_HARPOON(p_port + hp_scsidata_0, 0x00);
  4450. WR_HARPOON(p_port + hp_scsidata_1, 0x00);
  4451. WR_HARPOON(p_port + hp_portctrl_0, SCSI_BUS_EN);
  4452. WR_HARPOON(p_port + hp_scsisig,
  4453. (RD_HARPOON(p_port + hp_scsisig) | SCSI_MSG));
  4454. WR_HARPOON(p_port + hp_scsisig, (RD_HARPOON(p_port + hp_scsisig)
  4455. & ~SCSI_BSY));
  4456. FPT_Wait(p_port, TO_250ms);
  4457. return 1;
  4458. }
  4459. /*---------------------------------------------------------------------
  4460. *
  4461. * Function: FPT_scbusf
  4462. *
  4463. * Description: Release the SCSI bus and disable SCAM selection.
  4464. *
  4465. *---------------------------------------------------------------------*/
  4466. static void FPT_scbusf(u32 p_port)
  4467. {
  4468. WR_HARPOON(p_port + hp_page_ctrl,
  4469. (RD_HARPOON(p_port + hp_page_ctrl) | G_INT_DISABLE));
  4470. WR_HARPOON(p_port + hp_scsidata_0, 0x00);
  4471. WR_HARPOON(p_port + hp_portctrl_0, (RD_HARPOON(p_port + hp_portctrl_0)
  4472. & ~SCSI_BUS_EN));
  4473. WR_HARPOON(p_port + hp_scsisig, 0x00);
  4474. WR_HARPOON(p_port + hp_scsireset, (RD_HARPOON(p_port + hp_scsireset)
  4475. & ~SCAM_EN));
  4476. WR_HARPOON(p_port + hp_clkctrl_0, (RD_HARPOON(p_port + hp_clkctrl_0)
  4477. | ACTdeassert));
  4478. WRW_HARPOON((p_port + hp_intstat), (BUS_FREE | AUTO_INT | SCAM_SEL));
  4479. WR_HARPOON(p_port + hp_page_ctrl,
  4480. (RD_HARPOON(p_port + hp_page_ctrl) & ~G_INT_DISABLE));
  4481. }
  4482. /*---------------------------------------------------------------------
  4483. *
  4484. * Function: FPT_scasid
  4485. *
  4486. * Description: Assign an ID to all the SCAM devices.
  4487. *
  4488. *---------------------------------------------------------------------*/
  4489. static void FPT_scasid(unsigned char p_card, u32 p_port)
  4490. {
  4491. unsigned char temp_id_string[ID_STRING_LENGTH];
  4492. unsigned char i, k, scam_id;
  4493. unsigned char crcBytes[3];
  4494. struct nvram_info *pCurrNvRam;
  4495. unsigned short *pCrcBytes;
  4496. pCurrNvRam = FPT_BL_Card[p_card].pNvRamInfo;
  4497. i = 0;
  4498. while (!i) {
  4499. for (k = 0; k < ID_STRING_LENGTH; k++) {
  4500. temp_id_string[k] = (unsigned char)0x00;
  4501. }
  4502. FPT_scxferc(p_port, SYNC_PTRN);
  4503. FPT_scxferc(p_port, ASSIGN_ID);
  4504. if (!(FPT_sciso(p_port, &temp_id_string[0]))) {
  4505. if (pCurrNvRam) {
  4506. pCrcBytes = (unsigned short *)&crcBytes[0];
  4507. *pCrcBytes = FPT_CalcCrc16(&temp_id_string[0]);
  4508. crcBytes[2] = FPT_CalcLrc(&temp_id_string[0]);
  4509. temp_id_string[1] = crcBytes[2];
  4510. temp_id_string[2] = crcBytes[0];
  4511. temp_id_string[3] = crcBytes[1];
  4512. for (k = 4; k < ID_STRING_LENGTH; k++)
  4513. temp_id_string[k] = (unsigned char)0x00;
  4514. }
  4515. i = FPT_scmachid(p_card, temp_id_string);
  4516. if (i == CLR_PRIORITY) {
  4517. FPT_scxferc(p_port, MISC_CODE);
  4518. FPT_scxferc(p_port, CLR_P_FLAG);
  4519. i = 0; /*Not the last ID yet. */
  4520. }
  4521. else if (i != NO_ID_AVAIL) {
  4522. if (i < 8)
  4523. FPT_scxferc(p_port, ID_0_7);
  4524. else
  4525. FPT_scxferc(p_port, ID_8_F);
  4526. scam_id = (i & (unsigned char)0x07);
  4527. for (k = 1; k < 0x08; k <<= 1)
  4528. if (!(k & i))
  4529. scam_id += 0x08; /*Count number of zeros in DB0-3. */
  4530. FPT_scxferc(p_port, scam_id);
  4531. i = 0; /*Not the last ID yet. */
  4532. }
  4533. }
  4534. else {
  4535. i = 1;
  4536. }
  4537. } /*End while */
  4538. FPT_scxferc(p_port, SYNC_PTRN);
  4539. FPT_scxferc(p_port, CFG_CMPLT);
  4540. }
  4541. /*---------------------------------------------------------------------
  4542. *
  4543. * Function: FPT_scsel
  4544. *
  4545. * Description: Select all the SCAM devices.
  4546. *
  4547. *---------------------------------------------------------------------*/
  4548. static void FPT_scsel(u32 p_port)
  4549. {
  4550. WR_HARPOON(p_port + hp_scsisig, SCSI_SEL);
  4551. FPT_scwiros(p_port, SCSI_MSG);
  4552. WR_HARPOON(p_port + hp_scsisig, (SCSI_SEL | SCSI_BSY));
  4553. WR_HARPOON(p_port + hp_scsisig,
  4554. (SCSI_SEL | SCSI_BSY | SCSI_IOBIT | SCSI_CD));
  4555. WR_HARPOON(p_port + hp_scsidata_0,
  4556. (unsigned char)(RD_HARPOON(p_port + hp_scsidata_0) |
  4557. (unsigned char)(BIT(7) + BIT(6))));
  4558. WR_HARPOON(p_port + hp_scsisig, (SCSI_BSY | SCSI_IOBIT | SCSI_CD));
  4559. FPT_scwiros(p_port, SCSI_SEL);
  4560. WR_HARPOON(p_port + hp_scsidata_0,
  4561. (unsigned char)(RD_HARPOON(p_port + hp_scsidata_0) &
  4562. ~(unsigned char)BIT(6)));
  4563. FPT_scwirod(p_port, BIT(6));
  4564. WR_HARPOON(p_port + hp_scsisig,
  4565. (SCSI_SEL | SCSI_BSY | SCSI_IOBIT | SCSI_CD));
  4566. }
  4567. /*---------------------------------------------------------------------
  4568. *
  4569. * Function: FPT_scxferc
  4570. *
  4571. * Description: Handshake the p_data (DB4-0) across the bus.
  4572. *
  4573. *---------------------------------------------------------------------*/
  4574. static unsigned char FPT_scxferc(u32 p_port, unsigned char p_data)
  4575. {
  4576. unsigned char curr_data, ret_data;
  4577. curr_data = p_data | BIT(7) | BIT(5); /*Start with DB7 & DB5 asserted. */
  4578. WR_HARPOON(p_port + hp_scsidata_0, curr_data);
  4579. curr_data &= ~BIT(7);
  4580. WR_HARPOON(p_port + hp_scsidata_0, curr_data);
  4581. FPT_scwirod(p_port, BIT(7)); /*Wait for DB7 to be released. */
  4582. while (!(RD_HARPOON(p_port + hp_scsidata_0) & BIT(5))) ;
  4583. ret_data = (RD_HARPOON(p_port + hp_scsidata_0) & (unsigned char)0x1F);
  4584. curr_data |= BIT(6);
  4585. WR_HARPOON(p_port + hp_scsidata_0, curr_data);
  4586. curr_data &= ~BIT(5);
  4587. WR_HARPOON(p_port + hp_scsidata_0, curr_data);
  4588. FPT_scwirod(p_port, BIT(5)); /*Wait for DB5 to be released. */
  4589. curr_data &= ~(BIT(4) | BIT(3) | BIT(2) | BIT(1) | BIT(0)); /*Release data bits */
  4590. curr_data |= BIT(7);
  4591. WR_HARPOON(p_port + hp_scsidata_0, curr_data);
  4592. curr_data &= ~BIT(6);
  4593. WR_HARPOON(p_port + hp_scsidata_0, curr_data);
  4594. FPT_scwirod(p_port, BIT(6)); /*Wait for DB6 to be released. */
  4595. return ret_data;
  4596. }
  4597. /*---------------------------------------------------------------------
  4598. *
  4599. * Function: FPT_scsendi
  4600. *
  4601. * Description: Transfer our Identification string to determine if we
  4602. * will be the dominant master.
  4603. *
  4604. *---------------------------------------------------------------------*/
  4605. static unsigned char FPT_scsendi(u32 p_port, unsigned char p_id_string[])
  4606. {
  4607. unsigned char ret_data, byte_cnt, bit_cnt, defer;
  4608. defer = 0;
  4609. for (byte_cnt = 0; byte_cnt < ID_STRING_LENGTH; byte_cnt++) {
  4610. for (bit_cnt = 0x80; bit_cnt != 0; bit_cnt >>= 1) {
  4611. if (defer)
  4612. ret_data = FPT_scxferc(p_port, 00);
  4613. else if (p_id_string[byte_cnt] & bit_cnt)
  4614. ret_data = FPT_scxferc(p_port, 02);
  4615. else {
  4616. ret_data = FPT_scxferc(p_port, 01);
  4617. if (ret_data & 02)
  4618. defer = 1;
  4619. }
  4620. if ((ret_data & 0x1C) == 0x10)
  4621. return 0x00; /*End of isolation stage, we won! */
  4622. if (ret_data & 0x1C)
  4623. return 0xFF;
  4624. if ((defer) && (!(ret_data & 0x1F)))
  4625. return 0x01; /*End of isolation stage, we lost. */
  4626. } /*bit loop */
  4627. } /*byte loop */
  4628. if (defer)
  4629. return 0x01; /*We lost */
  4630. else
  4631. return 0; /*We WON! Yeeessss! */
  4632. }
  4633. /*---------------------------------------------------------------------
  4634. *
  4635. * Function: FPT_sciso
  4636. *
  4637. * Description: Transfer the Identification string.
  4638. *
  4639. *---------------------------------------------------------------------*/
  4640. static unsigned char FPT_sciso(u32 p_port, unsigned char p_id_string[])
  4641. {
  4642. unsigned char ret_data, the_data, byte_cnt, bit_cnt;
  4643. the_data = 0;
  4644. for (byte_cnt = 0; byte_cnt < ID_STRING_LENGTH; byte_cnt++) {
  4645. for (bit_cnt = 0; bit_cnt < 8; bit_cnt++) {
  4646. ret_data = FPT_scxferc(p_port, 0);
  4647. if (ret_data & 0xFC)
  4648. return 0xFF;
  4649. else {
  4650. the_data <<= 1;
  4651. if (ret_data & BIT(1)) {
  4652. the_data |= 1;
  4653. }
  4654. }
  4655. if ((ret_data & 0x1F) == 0) {
  4656. /*
  4657. if(bit_cnt != 0 || bit_cnt != 8)
  4658. {
  4659. byte_cnt = 0;
  4660. bit_cnt = 0;
  4661. FPT_scxferc(p_port, SYNC_PTRN);
  4662. FPT_scxferc(p_port, ASSIGN_ID);
  4663. continue;
  4664. }
  4665. */
  4666. if (byte_cnt)
  4667. return 0x00;
  4668. else
  4669. return 0xFF;
  4670. }
  4671. } /*bit loop */
  4672. p_id_string[byte_cnt] = the_data;
  4673. } /*byte loop */
  4674. return 0;
  4675. }
  4676. /*---------------------------------------------------------------------
  4677. *
  4678. * Function: FPT_scwirod
  4679. *
  4680. * Description: Sample the SCSI data bus making sure the signal has been
  4681. * deasserted for the correct number of consecutive samples.
  4682. *
  4683. *---------------------------------------------------------------------*/
  4684. static void FPT_scwirod(u32 p_port, unsigned char p_data_bit)
  4685. {
  4686. unsigned char i;
  4687. i = 0;
  4688. while (i < MAX_SCSI_TAR) {
  4689. if (RD_HARPOON(p_port + hp_scsidata_0) & p_data_bit)
  4690. i = 0;
  4691. else
  4692. i++;
  4693. }
  4694. }
  4695. /*---------------------------------------------------------------------
  4696. *
  4697. * Function: FPT_scwiros
  4698. *
  4699. * Description: Sample the SCSI Signal lines making sure the signal has been
  4700. * deasserted for the correct number of consecutive samples.
  4701. *
  4702. *---------------------------------------------------------------------*/
  4703. static void FPT_scwiros(u32 p_port, unsigned char p_data_bit)
  4704. {
  4705. unsigned char i;
  4706. i = 0;
  4707. while (i < MAX_SCSI_TAR) {
  4708. if (RD_HARPOON(p_port + hp_scsisig) & p_data_bit)
  4709. i = 0;
  4710. else
  4711. i++;
  4712. }
  4713. }
  4714. /*---------------------------------------------------------------------
  4715. *
  4716. * Function: FPT_scvalq
  4717. *
  4718. * Description: Make sure we received a valid data byte.
  4719. *
  4720. *---------------------------------------------------------------------*/
  4721. static unsigned char FPT_scvalq(unsigned char p_quintet)
  4722. {
  4723. unsigned char count;
  4724. for (count = 1; count < 0x08; count <<= 1) {
  4725. if (!(p_quintet & count))
  4726. p_quintet -= 0x80;
  4727. }
  4728. if (p_quintet & 0x18)
  4729. return 0;
  4730. else
  4731. return 1;
  4732. }
  4733. /*---------------------------------------------------------------------
  4734. *
  4735. * Function: FPT_scsell
  4736. *
  4737. * Description: Select the specified device ID using a selection timeout
  4738. * less than 4ms. If somebody responds then it is a legacy
  4739. * drive and this ID must be marked as such.
  4740. *
  4741. *---------------------------------------------------------------------*/
  4742. static unsigned char FPT_scsell(u32 p_port, unsigned char targ_id)
  4743. {
  4744. unsigned long i;
  4745. WR_HARPOON(p_port + hp_page_ctrl,
  4746. (RD_HARPOON(p_port + hp_page_ctrl) | G_INT_DISABLE));
  4747. ARAM_ACCESS(p_port);
  4748. WR_HARPOON(p_port + hp_addstat,
  4749. (RD_HARPOON(p_port + hp_addstat) | SCAM_TIMER));
  4750. WR_HARPOON(p_port + hp_seltimeout, TO_4ms);
  4751. for (i = p_port + CMD_STRT; i < p_port + CMD_STRT + 12; i += 2) {
  4752. WRW_HARPOON(i, (MPM_OP + ACOMMAND));
  4753. }
  4754. WRW_HARPOON(i, (BRH_OP + ALWAYS + NP));
  4755. WRW_HARPOON((p_port + hp_intstat),
  4756. (RESET | TIMEOUT | SEL | BUS_FREE | AUTO_INT));
  4757. WR_HARPOON(p_port + hp_select_id, targ_id);
  4758. WR_HARPOON(p_port + hp_portctrl_0, SCSI_PORT);
  4759. WR_HARPOON(p_port + hp_autostart_3, (SELECT | CMD_ONLY_STRT));
  4760. WR_HARPOON(p_port + hp_scsictrl_0, (SEL_TAR | ENA_RESEL));
  4761. while (!(RDW_HARPOON((p_port + hp_intstat)) &
  4762. (RESET | PROG_HLT | TIMEOUT | AUTO_INT))) {
  4763. }
  4764. if (RDW_HARPOON((p_port + hp_intstat)) & RESET)
  4765. FPT_Wait(p_port, TO_250ms);
  4766. DISABLE_AUTO(p_port);
  4767. WR_HARPOON(p_port + hp_addstat,
  4768. (RD_HARPOON(p_port + hp_addstat) & ~SCAM_TIMER));
  4769. WR_HARPOON(p_port + hp_seltimeout, TO_290ms);
  4770. SGRAM_ACCESS(p_port);
  4771. if (RDW_HARPOON((p_port + hp_intstat)) & (RESET | TIMEOUT)) {
  4772. WRW_HARPOON((p_port + hp_intstat),
  4773. (RESET | TIMEOUT | SEL | BUS_FREE | PHASE));
  4774. WR_HARPOON(p_port + hp_page_ctrl,
  4775. (RD_HARPOON(p_port + hp_page_ctrl) &
  4776. ~G_INT_DISABLE));
  4777. return 0; /*No legacy device */
  4778. }
  4779. else {
  4780. while (!(RDW_HARPOON((p_port + hp_intstat)) & BUS_FREE)) {
  4781. if (RD_HARPOON(p_port + hp_scsisig) & SCSI_REQ) {
  4782. WR_HARPOON(p_port + hp_scsisig,
  4783. (SCSI_ACK + S_ILL_PH));
  4784. ACCEPT_MSG(p_port);
  4785. }
  4786. }
  4787. WRW_HARPOON((p_port + hp_intstat), CLR_ALL_INT_1);
  4788. WR_HARPOON(p_port + hp_page_ctrl,
  4789. (RD_HARPOON(p_port + hp_page_ctrl) &
  4790. ~G_INT_DISABLE));
  4791. return 1; /*Found one of them oldies! */
  4792. }
  4793. }
  4794. /*---------------------------------------------------------------------
  4795. *
  4796. * Function: FPT_scwtsel
  4797. *
  4798. * Description: Wait to be selected by another SCAM initiator.
  4799. *
  4800. *---------------------------------------------------------------------*/
  4801. static void FPT_scwtsel(u32 p_port)
  4802. {
  4803. while (!(RDW_HARPOON((p_port + hp_intstat)) & SCAM_SEL)) {
  4804. }
  4805. }
  4806. /*---------------------------------------------------------------------
  4807. *
  4808. * Function: FPT_inisci
  4809. *
  4810. * Description: Setup the data Structure with the info from the EEPROM.
  4811. *
  4812. *---------------------------------------------------------------------*/
  4813. static void FPT_inisci(unsigned char p_card, u32 p_port, unsigned char p_our_id)
  4814. {
  4815. unsigned char i, k, max_id;
  4816. unsigned short ee_data;
  4817. struct nvram_info *pCurrNvRam;
  4818. pCurrNvRam = FPT_BL_Card[p_card].pNvRamInfo;
  4819. if (RD_HARPOON(p_port + hp_page_ctrl) & NARROW_SCSI_CARD)
  4820. max_id = 0x08;
  4821. else
  4822. max_id = 0x10;
  4823. if (pCurrNvRam) {
  4824. for (i = 0; i < max_id; i++) {
  4825. for (k = 0; k < 4; k++)
  4826. FPT_scamInfo[i].id_string[k] =
  4827. pCurrNvRam->niScamTbl[i][k];
  4828. for (k = 4; k < ID_STRING_LENGTH; k++)
  4829. FPT_scamInfo[i].id_string[k] =
  4830. (unsigned char)0x00;
  4831. if (FPT_scamInfo[i].id_string[0] == 0x00)
  4832. FPT_scamInfo[i].state = ID_UNUSED; /*Default to unused ID. */
  4833. else
  4834. FPT_scamInfo[i].state = ID_UNASSIGNED; /*Default to unassigned ID. */
  4835. }
  4836. } else {
  4837. for (i = 0; i < max_id; i++) {
  4838. for (k = 0; k < ID_STRING_LENGTH; k += 2) {
  4839. ee_data =
  4840. FPT_utilEERead(p_port,
  4841. (unsigned
  4842. short)((EE_SCAMBASE / 2) +
  4843. (unsigned short)(i *
  4844. ((unsigned short)ID_STRING_LENGTH / 2)) + (unsigned short)(k / 2)));
  4845. FPT_scamInfo[i].id_string[k] =
  4846. (unsigned char)ee_data;
  4847. ee_data >>= 8;
  4848. FPT_scamInfo[i].id_string[k + 1] =
  4849. (unsigned char)ee_data;
  4850. }
  4851. if ((FPT_scamInfo[i].id_string[0] == 0x00) ||
  4852. (FPT_scamInfo[i].id_string[0] == 0xFF))
  4853. FPT_scamInfo[i].state = ID_UNUSED; /*Default to unused ID. */
  4854. else
  4855. FPT_scamInfo[i].state = ID_UNASSIGNED; /*Default to unassigned ID. */
  4856. }
  4857. }
  4858. for (k = 0; k < ID_STRING_LENGTH; k++)
  4859. FPT_scamInfo[p_our_id].id_string[k] = FPT_scamHAString[k];
  4860. }
  4861. /*---------------------------------------------------------------------
  4862. *
  4863. * Function: FPT_scmachid
  4864. *
  4865. * Description: Match the Device ID string with our values stored in
  4866. * the EEPROM.
  4867. *
  4868. *---------------------------------------------------------------------*/
  4869. static unsigned char FPT_scmachid(unsigned char p_card,
  4870. unsigned char p_id_string[])
  4871. {
  4872. unsigned char i, k, match;
  4873. for (i = 0; i < MAX_SCSI_TAR; i++) {
  4874. match = 1;
  4875. for (k = 0; k < ID_STRING_LENGTH; k++) {
  4876. if (p_id_string[k] != FPT_scamInfo[i].id_string[k])
  4877. match = 0;
  4878. }
  4879. if (match) {
  4880. FPT_scamInfo[i].state = ID_ASSIGNED;
  4881. return i;
  4882. }
  4883. }
  4884. if (p_id_string[0] & BIT(5))
  4885. i = 8;
  4886. else
  4887. i = MAX_SCSI_TAR;
  4888. if (((p_id_string[0] & 0x06) == 0x02)
  4889. || ((p_id_string[0] & 0x06) == 0x04))
  4890. match = p_id_string[1] & (unsigned char)0x1F;
  4891. else
  4892. match = 7;
  4893. while (i > 0) {
  4894. i--;
  4895. if (FPT_scamInfo[match].state == ID_UNUSED) {
  4896. for (k = 0; k < ID_STRING_LENGTH; k++) {
  4897. FPT_scamInfo[match].id_string[k] =
  4898. p_id_string[k];
  4899. }
  4900. FPT_scamInfo[match].state = ID_ASSIGNED;
  4901. if (FPT_BL_Card[p_card].pNvRamInfo == NULL)
  4902. FPT_BL_Card[p_card].globalFlags |=
  4903. F_UPDATE_EEPROM;
  4904. return match;
  4905. }
  4906. match--;
  4907. if (match == 0xFF) {
  4908. if (p_id_string[0] & BIT(5))
  4909. match = 7;
  4910. else
  4911. match = MAX_SCSI_TAR - 1;
  4912. }
  4913. }
  4914. if (p_id_string[0] & BIT(7)) {
  4915. return CLR_PRIORITY;
  4916. }
  4917. if (p_id_string[0] & BIT(5))
  4918. i = 8;
  4919. else
  4920. i = MAX_SCSI_TAR;
  4921. if (((p_id_string[0] & 0x06) == 0x02)
  4922. || ((p_id_string[0] & 0x06) == 0x04))
  4923. match = p_id_string[1] & (unsigned char)0x1F;
  4924. else
  4925. match = 7;
  4926. while (i > 0) {
  4927. i--;
  4928. if (FPT_scamInfo[match].state == ID_UNASSIGNED) {
  4929. for (k = 0; k < ID_STRING_LENGTH; k++) {
  4930. FPT_scamInfo[match].id_string[k] =
  4931. p_id_string[k];
  4932. }
  4933. FPT_scamInfo[match].id_string[0] |= BIT(7);
  4934. FPT_scamInfo[match].state = ID_ASSIGNED;
  4935. if (FPT_BL_Card[p_card].pNvRamInfo == NULL)
  4936. FPT_BL_Card[p_card].globalFlags |=
  4937. F_UPDATE_EEPROM;
  4938. return match;
  4939. }
  4940. match--;
  4941. if (match == 0xFF) {
  4942. if (p_id_string[0] & BIT(5))
  4943. match = 7;
  4944. else
  4945. match = MAX_SCSI_TAR - 1;
  4946. }
  4947. }
  4948. return NO_ID_AVAIL;
  4949. }
  4950. /*---------------------------------------------------------------------
  4951. *
  4952. * Function: FPT_scsavdi
  4953. *
  4954. * Description: Save off the device SCAM ID strings.
  4955. *
  4956. *---------------------------------------------------------------------*/
  4957. static void FPT_scsavdi(unsigned char p_card, u32 p_port)
  4958. {
  4959. unsigned char i, k, max_id;
  4960. unsigned short ee_data, sum_data;
  4961. sum_data = 0x0000;
  4962. for (i = 1; i < EE_SCAMBASE / 2; i++) {
  4963. sum_data += FPT_utilEERead(p_port, i);
  4964. }
  4965. FPT_utilEEWriteOnOff(p_port, 1); /* Enable write access to the EEPROM */
  4966. if (RD_HARPOON(p_port + hp_page_ctrl) & NARROW_SCSI_CARD)
  4967. max_id = 0x08;
  4968. else
  4969. max_id = 0x10;
  4970. for (i = 0; i < max_id; i++) {
  4971. for (k = 0; k < ID_STRING_LENGTH; k += 2) {
  4972. ee_data = FPT_scamInfo[i].id_string[k + 1];
  4973. ee_data <<= 8;
  4974. ee_data |= FPT_scamInfo[i].id_string[k];
  4975. sum_data += ee_data;
  4976. FPT_utilEEWrite(p_port, ee_data,
  4977. (unsigned short)((EE_SCAMBASE / 2) +
  4978. (unsigned short)(i *
  4979. ((unsigned short)ID_STRING_LENGTH / 2)) + (unsigned short)(k / 2)));
  4980. }
  4981. }
  4982. FPT_utilEEWrite(p_port, sum_data, EEPROM_CHECK_SUM / 2);
  4983. FPT_utilEEWriteOnOff(p_port, 0); /* Turn off write access */
  4984. }
  4985. /*---------------------------------------------------------------------
  4986. *
  4987. * Function: FPT_XbowInit
  4988. *
  4989. * Description: Setup the Xbow for normal operation.
  4990. *
  4991. *---------------------------------------------------------------------*/
  4992. static void FPT_XbowInit(u32 port, unsigned char ScamFlg)
  4993. {
  4994. unsigned char i;
  4995. i = RD_HARPOON(port + hp_page_ctrl);
  4996. WR_HARPOON(port + hp_page_ctrl, (unsigned char)(i | G_INT_DISABLE));
  4997. WR_HARPOON(port + hp_scsireset, 0x00);
  4998. WR_HARPOON(port + hp_portctrl_1, HOST_MODE8);
  4999. WR_HARPOON(port + hp_scsireset, (DMA_RESET | HPSCSI_RESET | PROG_RESET |
  5000. FIFO_CLR));
  5001. WR_HARPOON(port + hp_scsireset, SCSI_INI);
  5002. WR_HARPOON(port + hp_clkctrl_0, CLKCTRL_DEFAULT);
  5003. WR_HARPOON(port + hp_scsisig, 0x00); /* Clear any signals we might */
  5004. WR_HARPOON(port + hp_scsictrl_0, ENA_SCAM_SEL);
  5005. WRW_HARPOON((port + hp_intstat), CLR_ALL_INT);
  5006. FPT_default_intena = RESET | RSEL | PROG_HLT | TIMEOUT |
  5007. BUS_FREE | XFER_CNT_0 | AUTO_INT;
  5008. if ((ScamFlg & SCAM_ENABLED) && (ScamFlg & SCAM_LEVEL2))
  5009. FPT_default_intena |= SCAM_SEL;
  5010. WRW_HARPOON((port + hp_intena), FPT_default_intena);
  5011. WR_HARPOON(port + hp_seltimeout, TO_290ms);
  5012. /* Turn on SCSI_MODE8 for narrow cards to fix the
  5013. strapping issue with the DUAL CHANNEL card */
  5014. if (RD_HARPOON(port + hp_page_ctrl) & NARROW_SCSI_CARD)
  5015. WR_HARPOON(port + hp_addstat, SCSI_MODE8);
  5016. WR_HARPOON(port + hp_page_ctrl, i);
  5017. }
  5018. /*---------------------------------------------------------------------
  5019. *
  5020. * Function: FPT_BusMasterInit
  5021. *
  5022. * Description: Initialize the BusMaster for normal operations.
  5023. *
  5024. *---------------------------------------------------------------------*/
  5025. static void FPT_BusMasterInit(u32 p_port)
  5026. {
  5027. WR_HARPOON(p_port + hp_sys_ctrl, DRVR_RST);
  5028. WR_HARPOON(p_port + hp_sys_ctrl, 0x00);
  5029. WR_HARPOON(p_port + hp_host_blk_cnt, XFER_BLK64);
  5030. WR_HARPOON(p_port + hp_bm_ctrl, (BMCTRL_DEFAULT));
  5031. WR_HARPOON(p_port + hp_ee_ctrl, (SCSI_TERM_ENA_H));
  5032. RD_HARPOON(p_port + hp_int_status); /*Clear interrupts. */
  5033. WR_HARPOON(p_port + hp_int_mask, (INT_CMD_COMPL | SCSI_INTERRUPT));
  5034. WR_HARPOON(p_port + hp_page_ctrl, (RD_HARPOON(p_port + hp_page_ctrl) &
  5035. ~SCATTER_EN));
  5036. }
  5037. /*---------------------------------------------------------------------
  5038. *
  5039. * Function: FPT_DiagEEPROM
  5040. *
  5041. * Description: Verfiy checksum and 'Key' and initialize the EEPROM if
  5042. * necessary.
  5043. *
  5044. *---------------------------------------------------------------------*/
  5045. static void FPT_DiagEEPROM(u32 p_port)
  5046. {
  5047. unsigned short index, temp, max_wd_cnt;
  5048. if (RD_HARPOON(p_port + hp_page_ctrl) & NARROW_SCSI_CARD)
  5049. max_wd_cnt = EEPROM_WD_CNT;
  5050. else
  5051. max_wd_cnt = EEPROM_WD_CNT * 2;
  5052. temp = FPT_utilEERead(p_port, FW_SIGNATURE / 2);
  5053. if (temp == 0x4641) {
  5054. for (index = 2; index < max_wd_cnt; index++) {
  5055. temp += FPT_utilEERead(p_port, index);
  5056. }
  5057. if (temp == FPT_utilEERead(p_port, EEPROM_CHECK_SUM / 2)) {
  5058. return; /*EEPROM is Okay so return now! */
  5059. }
  5060. }
  5061. FPT_utilEEWriteOnOff(p_port, (unsigned char)1);
  5062. for (index = 0; index < max_wd_cnt; index++) {
  5063. FPT_utilEEWrite(p_port, 0x0000, index);
  5064. }
  5065. temp = 0;
  5066. FPT_utilEEWrite(p_port, 0x4641, FW_SIGNATURE / 2);
  5067. temp += 0x4641;
  5068. FPT_utilEEWrite(p_port, 0x3920, MODEL_NUMB_0 / 2);
  5069. temp += 0x3920;
  5070. FPT_utilEEWrite(p_port, 0x3033, MODEL_NUMB_2 / 2);
  5071. temp += 0x3033;
  5072. FPT_utilEEWrite(p_port, 0x2020, MODEL_NUMB_4 / 2);
  5073. temp += 0x2020;
  5074. FPT_utilEEWrite(p_port, 0x70D3, SYSTEM_CONFIG / 2);
  5075. temp += 0x70D3;
  5076. FPT_utilEEWrite(p_port, 0x0010, BIOS_CONFIG / 2);
  5077. temp += 0x0010;
  5078. FPT_utilEEWrite(p_port, 0x0003, SCAM_CONFIG / 2);
  5079. temp += 0x0003;
  5080. FPT_utilEEWrite(p_port, 0x0007, ADAPTER_SCSI_ID / 2);
  5081. temp += 0x0007;
  5082. FPT_utilEEWrite(p_port, 0x0000, IGNORE_B_SCAN / 2);
  5083. temp += 0x0000;
  5084. FPT_utilEEWrite(p_port, 0x0000, SEND_START_ENA / 2);
  5085. temp += 0x0000;
  5086. FPT_utilEEWrite(p_port, 0x0000, DEVICE_ENABLE / 2);
  5087. temp += 0x0000;
  5088. FPT_utilEEWrite(p_port, 0x4242, SYNC_RATE_TBL01 / 2);
  5089. temp += 0x4242;
  5090. FPT_utilEEWrite(p_port, 0x4242, SYNC_RATE_TBL23 / 2);
  5091. temp += 0x4242;
  5092. FPT_utilEEWrite(p_port, 0x4242, SYNC_RATE_TBL45 / 2);
  5093. temp += 0x4242;
  5094. FPT_utilEEWrite(p_port, 0x4242, SYNC_RATE_TBL67 / 2);
  5095. temp += 0x4242;
  5096. FPT_utilEEWrite(p_port, 0x4242, SYNC_RATE_TBL89 / 2);
  5097. temp += 0x4242;
  5098. FPT_utilEEWrite(p_port, 0x4242, SYNC_RATE_TBLab / 2);
  5099. temp += 0x4242;
  5100. FPT_utilEEWrite(p_port, 0x4242, SYNC_RATE_TBLcd / 2);
  5101. temp += 0x4242;
  5102. FPT_utilEEWrite(p_port, 0x4242, SYNC_RATE_TBLef / 2);
  5103. temp += 0x4242;
  5104. FPT_utilEEWrite(p_port, 0x6C46, 64 / 2); /*PRODUCT ID */
  5105. temp += 0x6C46;
  5106. FPT_utilEEWrite(p_port, 0x7361, 66 / 2); /* FlashPoint LT */
  5107. temp += 0x7361;
  5108. FPT_utilEEWrite(p_port, 0x5068, 68 / 2);
  5109. temp += 0x5068;
  5110. FPT_utilEEWrite(p_port, 0x696F, 70 / 2);
  5111. temp += 0x696F;
  5112. FPT_utilEEWrite(p_port, 0x746E, 72 / 2);
  5113. temp += 0x746E;
  5114. FPT_utilEEWrite(p_port, 0x4C20, 74 / 2);
  5115. temp += 0x4C20;
  5116. FPT_utilEEWrite(p_port, 0x2054, 76 / 2);
  5117. temp += 0x2054;
  5118. FPT_utilEEWrite(p_port, 0x2020, 78 / 2);
  5119. temp += 0x2020;
  5120. index = ((EE_SCAMBASE / 2) + (7 * 16));
  5121. FPT_utilEEWrite(p_port, (0x0700 + TYPE_CODE0), index);
  5122. temp += (0x0700 + TYPE_CODE0);
  5123. index++;
  5124. FPT_utilEEWrite(p_port, 0x5542, index); /*Vendor ID code */
  5125. temp += 0x5542; /* BUSLOGIC */
  5126. index++;
  5127. FPT_utilEEWrite(p_port, 0x4C53, index);
  5128. temp += 0x4C53;
  5129. index++;
  5130. FPT_utilEEWrite(p_port, 0x474F, index);
  5131. temp += 0x474F;
  5132. index++;
  5133. FPT_utilEEWrite(p_port, 0x4349, index);
  5134. temp += 0x4349;
  5135. index++;
  5136. FPT_utilEEWrite(p_port, 0x5442, index); /*Vendor unique code */
  5137. temp += 0x5442; /* BT- 930 */
  5138. index++;
  5139. FPT_utilEEWrite(p_port, 0x202D, index);
  5140. temp += 0x202D;
  5141. index++;
  5142. FPT_utilEEWrite(p_port, 0x3339, index);
  5143. temp += 0x3339;
  5144. index++; /*Serial # */
  5145. FPT_utilEEWrite(p_port, 0x2030, index); /* 01234567 */
  5146. temp += 0x2030;
  5147. index++;
  5148. FPT_utilEEWrite(p_port, 0x5453, index);
  5149. temp += 0x5453;
  5150. index++;
  5151. FPT_utilEEWrite(p_port, 0x5645, index);
  5152. temp += 0x5645;
  5153. index++;
  5154. FPT_utilEEWrite(p_port, 0x2045, index);
  5155. temp += 0x2045;
  5156. index++;
  5157. FPT_utilEEWrite(p_port, 0x202F, index);
  5158. temp += 0x202F;
  5159. index++;
  5160. FPT_utilEEWrite(p_port, 0x4F4A, index);
  5161. temp += 0x4F4A;
  5162. index++;
  5163. FPT_utilEEWrite(p_port, 0x204E, index);
  5164. temp += 0x204E;
  5165. index++;
  5166. FPT_utilEEWrite(p_port, 0x3539, index);
  5167. temp += 0x3539;
  5168. FPT_utilEEWrite(p_port, temp, EEPROM_CHECK_SUM / 2);
  5169. FPT_utilEEWriteOnOff(p_port, (unsigned char)0);
  5170. }
  5171. /*---------------------------------------------------------------------
  5172. *
  5173. * Function: Queue Search Select
  5174. *
  5175. * Description: Try to find a new command to execute.
  5176. *
  5177. *---------------------------------------------------------------------*/
  5178. static void FPT_queueSearchSelect(struct sccb_card *pCurrCard,
  5179. unsigned char p_card)
  5180. {
  5181. unsigned char scan_ptr, lun;
  5182. struct sccb_mgr_tar_info *currTar_Info;
  5183. struct sccb *pOldSccb;
  5184. scan_ptr = pCurrCard->scanIndex;
  5185. do {
  5186. currTar_Info = &FPT_sccbMgrTbl[p_card][scan_ptr];
  5187. if ((pCurrCard->globalFlags & F_CONLUN_IO) &&
  5188. ((currTar_Info->TarStatus & TAR_TAG_Q_MASK) !=
  5189. TAG_Q_TRYING)) {
  5190. if (currTar_Info->TarSelQ_Cnt != 0) {
  5191. scan_ptr++;
  5192. if (scan_ptr == MAX_SCSI_TAR)
  5193. scan_ptr = 0;
  5194. for (lun = 0; lun < MAX_LUN; lun++) {
  5195. if (currTar_Info->TarLUNBusy[lun] == 0) {
  5196. pCurrCard->currentSCCB =
  5197. currTar_Info->TarSelQ_Head;
  5198. pOldSccb = NULL;
  5199. while ((pCurrCard->
  5200. currentSCCB != NULL)
  5201. && (lun !=
  5202. pCurrCard->
  5203. currentSCCB->Lun)) {
  5204. pOldSccb =
  5205. pCurrCard->
  5206. currentSCCB;
  5207. pCurrCard->currentSCCB =
  5208. (struct sccb
  5209. *)(pCurrCard->
  5210. currentSCCB)->
  5211. Sccb_forwardlink;
  5212. }
  5213. if (pCurrCard->currentSCCB ==
  5214. NULL)
  5215. continue;
  5216. if (pOldSccb != NULL) {
  5217. pOldSccb->
  5218. Sccb_forwardlink =
  5219. (struct sccb
  5220. *)(pCurrCard->
  5221. currentSCCB)->
  5222. Sccb_forwardlink;
  5223. pOldSccb->
  5224. Sccb_backlink =
  5225. (struct sccb
  5226. *)(pCurrCard->
  5227. currentSCCB)->
  5228. Sccb_backlink;
  5229. currTar_Info->
  5230. TarSelQ_Cnt--;
  5231. } else {
  5232. currTar_Info->
  5233. TarSelQ_Head =
  5234. (struct sccb
  5235. *)(pCurrCard->
  5236. currentSCCB)->
  5237. Sccb_forwardlink;
  5238. if (currTar_Info->
  5239. TarSelQ_Head ==
  5240. NULL) {
  5241. currTar_Info->
  5242. TarSelQ_Tail
  5243. = NULL;
  5244. currTar_Info->
  5245. TarSelQ_Cnt
  5246. = 0;
  5247. } else {
  5248. currTar_Info->
  5249. TarSelQ_Cnt--;
  5250. currTar_Info->
  5251. TarSelQ_Head->
  5252. Sccb_backlink
  5253. =
  5254. (struct sccb
  5255. *)NULL;
  5256. }
  5257. }
  5258. pCurrCard->scanIndex = scan_ptr;
  5259. pCurrCard->globalFlags |=
  5260. F_NEW_SCCB_CMD;
  5261. break;
  5262. }
  5263. }
  5264. }
  5265. else {
  5266. scan_ptr++;
  5267. if (scan_ptr == MAX_SCSI_TAR) {
  5268. scan_ptr = 0;
  5269. }
  5270. }
  5271. } else {
  5272. if ((currTar_Info->TarSelQ_Cnt != 0) &&
  5273. (currTar_Info->TarLUNBusy[0] == 0)) {
  5274. pCurrCard->currentSCCB =
  5275. currTar_Info->TarSelQ_Head;
  5276. currTar_Info->TarSelQ_Head =
  5277. (struct sccb *)(pCurrCard->currentSCCB)->
  5278. Sccb_forwardlink;
  5279. if (currTar_Info->TarSelQ_Head == NULL) {
  5280. currTar_Info->TarSelQ_Tail = NULL;
  5281. currTar_Info->TarSelQ_Cnt = 0;
  5282. } else {
  5283. currTar_Info->TarSelQ_Cnt--;
  5284. currTar_Info->TarSelQ_Head->
  5285. Sccb_backlink = (struct sccb *)NULL;
  5286. }
  5287. scan_ptr++;
  5288. if (scan_ptr == MAX_SCSI_TAR)
  5289. scan_ptr = 0;
  5290. pCurrCard->scanIndex = scan_ptr;
  5291. pCurrCard->globalFlags |= F_NEW_SCCB_CMD;
  5292. break;
  5293. }
  5294. else {
  5295. scan_ptr++;
  5296. if (scan_ptr == MAX_SCSI_TAR) {
  5297. scan_ptr = 0;
  5298. }
  5299. }
  5300. }
  5301. } while (scan_ptr != pCurrCard->scanIndex);
  5302. }
  5303. /*---------------------------------------------------------------------
  5304. *
  5305. * Function: Queue Select Fail
  5306. *
  5307. * Description: Add the current SCCB to the head of the Queue.
  5308. *
  5309. *---------------------------------------------------------------------*/
  5310. static void FPT_queueSelectFail(struct sccb_card *pCurrCard,
  5311. unsigned char p_card)
  5312. {
  5313. unsigned char thisTarg;
  5314. struct sccb_mgr_tar_info *currTar_Info;
  5315. if (pCurrCard->currentSCCB != NULL) {
  5316. thisTarg =
  5317. (unsigned char)(((struct sccb *)(pCurrCard->currentSCCB))->
  5318. TargID);
  5319. currTar_Info = &FPT_sccbMgrTbl[p_card][thisTarg];
  5320. pCurrCard->currentSCCB->Sccb_backlink = (struct sccb *)NULL;
  5321. pCurrCard->currentSCCB->Sccb_forwardlink =
  5322. currTar_Info->TarSelQ_Head;
  5323. if (currTar_Info->TarSelQ_Cnt == 0) {
  5324. currTar_Info->TarSelQ_Tail = pCurrCard->currentSCCB;
  5325. }
  5326. else {
  5327. currTar_Info->TarSelQ_Head->Sccb_backlink =
  5328. pCurrCard->currentSCCB;
  5329. }
  5330. currTar_Info->TarSelQ_Head = pCurrCard->currentSCCB;
  5331. pCurrCard->currentSCCB = NULL;
  5332. currTar_Info->TarSelQ_Cnt++;
  5333. }
  5334. }
  5335. /*---------------------------------------------------------------------
  5336. *
  5337. * Function: Queue Command Complete
  5338. *
  5339. * Description: Call the callback function with the current SCCB.
  5340. *
  5341. *---------------------------------------------------------------------*/
  5342. static void FPT_queueCmdComplete(struct sccb_card *pCurrCard,
  5343. struct sccb *p_sccb, unsigned char p_card)
  5344. {
  5345. unsigned char i, SCSIcmd;
  5346. CALL_BK_FN callback;
  5347. struct sccb_mgr_tar_info *currTar_Info;
  5348. SCSIcmd = p_sccb->Cdb[0];
  5349. if (!(p_sccb->Sccb_XferState & F_ALL_XFERRED)) {
  5350. if ((p_sccb->
  5351. ControlByte & (SCCB_DATA_XFER_OUT | SCCB_DATA_XFER_IN))
  5352. && (p_sccb->HostStatus == SCCB_COMPLETE)
  5353. && (p_sccb->TargetStatus != SSCHECK))
  5354. if ((SCSIcmd == SCSI_READ) ||
  5355. (SCSIcmd == SCSI_WRITE) ||
  5356. (SCSIcmd == SCSI_READ_EXTENDED) ||
  5357. (SCSIcmd == SCSI_WRITE_EXTENDED) ||
  5358. (SCSIcmd == SCSI_WRITE_AND_VERIFY) ||
  5359. (SCSIcmd == SCSI_START_STOP_UNIT) ||
  5360. (pCurrCard->globalFlags & F_NO_FILTER)
  5361. )
  5362. p_sccb->HostStatus = SCCB_DATA_UNDER_RUN;
  5363. }
  5364. if (p_sccb->SccbStatus == SCCB_IN_PROCESS) {
  5365. if (p_sccb->HostStatus || p_sccb->TargetStatus)
  5366. p_sccb->SccbStatus = SCCB_ERROR;
  5367. else
  5368. p_sccb->SccbStatus = SCCB_SUCCESS;
  5369. }
  5370. if (p_sccb->Sccb_XferState & F_AUTO_SENSE) {
  5371. p_sccb->CdbLength = p_sccb->Save_CdbLen;
  5372. for (i = 0; i < 6; i++) {
  5373. p_sccb->Cdb[i] = p_sccb->Save_Cdb[i];
  5374. }
  5375. }
  5376. if ((p_sccb->OperationCode == RESIDUAL_SG_COMMAND) ||
  5377. (p_sccb->OperationCode == RESIDUAL_COMMAND)) {
  5378. FPT_utilUpdateResidual(p_sccb);
  5379. }
  5380. pCurrCard->cmdCounter--;
  5381. if (!pCurrCard->cmdCounter) {
  5382. if (pCurrCard->globalFlags & F_GREEN_PC) {
  5383. WR_HARPOON(pCurrCard->ioPort + hp_clkctrl_0,
  5384. (PWR_DWN | CLKCTRL_DEFAULT));
  5385. WR_HARPOON(pCurrCard->ioPort + hp_sys_ctrl, STOP_CLK);
  5386. }
  5387. WR_HARPOON(pCurrCard->ioPort + hp_semaphore,
  5388. (RD_HARPOON(pCurrCard->ioPort + hp_semaphore) &
  5389. ~SCCB_MGR_ACTIVE));
  5390. }
  5391. if (pCurrCard->discQCount != 0) {
  5392. currTar_Info = &FPT_sccbMgrTbl[p_card][p_sccb->TargID];
  5393. if (((pCurrCard->globalFlags & F_CONLUN_IO) &&
  5394. ((currTar_Info->TarStatus & TAR_TAG_Q_MASK) !=
  5395. TAG_Q_TRYING))) {
  5396. pCurrCard->discQCount--;
  5397. pCurrCard->discQ_Tbl[currTar_Info->
  5398. LunDiscQ_Idx[p_sccb->Lun]] = NULL;
  5399. } else {
  5400. if (p_sccb->Sccb_tag) {
  5401. pCurrCard->discQCount--;
  5402. pCurrCard->discQ_Tbl[p_sccb->Sccb_tag] = NULL;
  5403. } else {
  5404. pCurrCard->discQCount--;
  5405. pCurrCard->discQ_Tbl[currTar_Info->
  5406. LunDiscQ_Idx[0]] = NULL;
  5407. }
  5408. }
  5409. }
  5410. callback = (CALL_BK_FN) p_sccb->SccbCallback;
  5411. callback(p_sccb);
  5412. pCurrCard->globalFlags |= F_NEW_SCCB_CMD;
  5413. pCurrCard->currentSCCB = NULL;
  5414. }
  5415. /*---------------------------------------------------------------------
  5416. *
  5417. * Function: Queue Disconnect
  5418. *
  5419. * Description: Add SCCB to our disconnect array.
  5420. *
  5421. *---------------------------------------------------------------------*/
  5422. static void FPT_queueDisconnect(struct sccb *p_sccb, unsigned char p_card)
  5423. {
  5424. struct sccb_mgr_tar_info *currTar_Info;
  5425. currTar_Info = &FPT_sccbMgrTbl[p_card][p_sccb->TargID];
  5426. if (((FPT_BL_Card[p_card].globalFlags & F_CONLUN_IO) &&
  5427. ((currTar_Info->TarStatus & TAR_TAG_Q_MASK) != TAG_Q_TRYING))) {
  5428. FPT_BL_Card[p_card].discQ_Tbl[currTar_Info->
  5429. LunDiscQ_Idx[p_sccb->Lun]] =
  5430. p_sccb;
  5431. } else {
  5432. if (p_sccb->Sccb_tag) {
  5433. FPT_BL_Card[p_card].discQ_Tbl[p_sccb->Sccb_tag] =
  5434. p_sccb;
  5435. FPT_sccbMgrTbl[p_card][p_sccb->TargID].TarLUNBusy[0] =
  5436. 0;
  5437. FPT_sccbMgrTbl[p_card][p_sccb->TargID].TarTagQ_Cnt++;
  5438. } else {
  5439. FPT_BL_Card[p_card].discQ_Tbl[currTar_Info->
  5440. LunDiscQ_Idx[0]] = p_sccb;
  5441. }
  5442. }
  5443. FPT_BL_Card[p_card].currentSCCB = NULL;
  5444. }
  5445. /*---------------------------------------------------------------------
  5446. *
  5447. * Function: Queue Flush SCCB
  5448. *
  5449. * Description: Flush all SCCB's back to the host driver for this target.
  5450. *
  5451. *---------------------------------------------------------------------*/
  5452. static void FPT_queueFlushSccb(unsigned char p_card, unsigned char error_code)
  5453. {
  5454. unsigned char qtag, thisTarg;
  5455. struct sccb *currSCCB;
  5456. struct sccb_mgr_tar_info *currTar_Info;
  5457. currSCCB = FPT_BL_Card[p_card].currentSCCB;
  5458. if (currSCCB != NULL) {
  5459. thisTarg = (unsigned char)currSCCB->TargID;
  5460. currTar_Info = &FPT_sccbMgrTbl[p_card][thisTarg];
  5461. for (qtag = 0; qtag < QUEUE_DEPTH; qtag++) {
  5462. if (FPT_BL_Card[p_card].discQ_Tbl[qtag] &&
  5463. (FPT_BL_Card[p_card].discQ_Tbl[qtag]->TargID ==
  5464. thisTarg)) {
  5465. FPT_BL_Card[p_card].discQ_Tbl[qtag]->
  5466. HostStatus = (unsigned char)error_code;
  5467. FPT_queueCmdComplete(&FPT_BL_Card[p_card],
  5468. FPT_BL_Card[p_card].
  5469. discQ_Tbl[qtag], p_card);
  5470. FPT_BL_Card[p_card].discQ_Tbl[qtag] = NULL;
  5471. currTar_Info->TarTagQ_Cnt--;
  5472. }
  5473. }
  5474. }
  5475. }
  5476. /*---------------------------------------------------------------------
  5477. *
  5478. * Function: Queue Flush Target SCCB
  5479. *
  5480. * Description: Flush all SCCB's back to the host driver for this target.
  5481. *
  5482. *---------------------------------------------------------------------*/
  5483. static void FPT_queueFlushTargSccb(unsigned char p_card, unsigned char thisTarg,
  5484. unsigned char error_code)
  5485. {
  5486. unsigned char qtag;
  5487. struct sccb_mgr_tar_info *currTar_Info;
  5488. currTar_Info = &FPT_sccbMgrTbl[p_card][thisTarg];
  5489. for (qtag = 0; qtag < QUEUE_DEPTH; qtag++) {
  5490. if (FPT_BL_Card[p_card].discQ_Tbl[qtag] &&
  5491. (FPT_BL_Card[p_card].discQ_Tbl[qtag]->TargID == thisTarg)) {
  5492. FPT_BL_Card[p_card].discQ_Tbl[qtag]->HostStatus =
  5493. (unsigned char)error_code;
  5494. FPT_queueCmdComplete(&FPT_BL_Card[p_card],
  5495. FPT_BL_Card[p_card].
  5496. discQ_Tbl[qtag], p_card);
  5497. FPT_BL_Card[p_card].discQ_Tbl[qtag] = NULL;
  5498. currTar_Info->TarTagQ_Cnt--;
  5499. }
  5500. }
  5501. }
  5502. static void FPT_queueAddSccb(struct sccb *p_SCCB, unsigned char p_card)
  5503. {
  5504. struct sccb_mgr_tar_info *currTar_Info;
  5505. currTar_Info = &FPT_sccbMgrTbl[p_card][p_SCCB->TargID];
  5506. p_SCCB->Sccb_forwardlink = NULL;
  5507. p_SCCB->Sccb_backlink = currTar_Info->TarSelQ_Tail;
  5508. if (currTar_Info->TarSelQ_Cnt == 0) {
  5509. currTar_Info->TarSelQ_Head = p_SCCB;
  5510. }
  5511. else {
  5512. currTar_Info->TarSelQ_Tail->Sccb_forwardlink = p_SCCB;
  5513. }
  5514. currTar_Info->TarSelQ_Tail = p_SCCB;
  5515. currTar_Info->TarSelQ_Cnt++;
  5516. }
  5517. /*---------------------------------------------------------------------
  5518. *
  5519. * Function: Queue Find SCCB
  5520. *
  5521. * Description: Search the target select Queue for this SCCB, and
  5522. * remove it if found.
  5523. *
  5524. *---------------------------------------------------------------------*/
  5525. static unsigned char FPT_queueFindSccb(struct sccb *p_SCCB,
  5526. unsigned char p_card)
  5527. {
  5528. struct sccb *q_ptr;
  5529. struct sccb_mgr_tar_info *currTar_Info;
  5530. currTar_Info = &FPT_sccbMgrTbl[p_card][p_SCCB->TargID];
  5531. q_ptr = currTar_Info->TarSelQ_Head;
  5532. while (q_ptr != NULL) {
  5533. if (q_ptr == p_SCCB) {
  5534. if (currTar_Info->TarSelQ_Head == q_ptr) {
  5535. currTar_Info->TarSelQ_Head =
  5536. q_ptr->Sccb_forwardlink;
  5537. }
  5538. if (currTar_Info->TarSelQ_Tail == q_ptr) {
  5539. currTar_Info->TarSelQ_Tail =
  5540. q_ptr->Sccb_backlink;
  5541. }
  5542. if (q_ptr->Sccb_forwardlink != NULL) {
  5543. q_ptr->Sccb_forwardlink->Sccb_backlink =
  5544. q_ptr->Sccb_backlink;
  5545. }
  5546. if (q_ptr->Sccb_backlink != NULL) {
  5547. q_ptr->Sccb_backlink->Sccb_forwardlink =
  5548. q_ptr->Sccb_forwardlink;
  5549. }
  5550. currTar_Info->TarSelQ_Cnt--;
  5551. return 1;
  5552. }
  5553. else {
  5554. q_ptr = q_ptr->Sccb_forwardlink;
  5555. }
  5556. }
  5557. return 0;
  5558. }
  5559. /*---------------------------------------------------------------------
  5560. *
  5561. * Function: Utility Update Residual Count
  5562. *
  5563. * Description: Update the XferCnt to the remaining byte count.
  5564. * If we transferred all the data then just write zero.
  5565. * If Non-SG transfer then report Total Cnt - Actual Transfer
  5566. * Cnt. For SG transfers add the count fields of all
  5567. * remaining SG elements, as well as any partial remaining
  5568. * element.
  5569. *
  5570. *---------------------------------------------------------------------*/
  5571. static void FPT_utilUpdateResidual(struct sccb *p_SCCB)
  5572. {
  5573. unsigned long partial_cnt;
  5574. unsigned int sg_index;
  5575. struct blogic_sg_seg *segp;
  5576. if (p_SCCB->Sccb_XferState & F_ALL_XFERRED) {
  5577. p_SCCB->DataLength = 0x0000;
  5578. }
  5579. else if (p_SCCB->Sccb_XferState & F_SG_XFER) {
  5580. partial_cnt = 0x0000;
  5581. sg_index = p_SCCB->Sccb_sgseg;
  5582. if (p_SCCB->Sccb_SGoffset) {
  5583. partial_cnt = p_SCCB->Sccb_SGoffset;
  5584. sg_index++;
  5585. }
  5586. while (((unsigned long)sg_index *
  5587. (unsigned long)SG_ELEMENT_SIZE) < p_SCCB->DataLength) {
  5588. segp = (struct blogic_sg_seg *)(p_SCCB->DataPointer) +
  5589. (sg_index * 2);
  5590. partial_cnt += segp->segbytes;
  5591. sg_index++;
  5592. }
  5593. p_SCCB->DataLength = partial_cnt;
  5594. }
  5595. else {
  5596. p_SCCB->DataLength -= p_SCCB->Sccb_ATC;
  5597. }
  5598. }
  5599. /*---------------------------------------------------------------------
  5600. *
  5601. * Function: Wait 1 Second
  5602. *
  5603. * Description: Wait for 1 second.
  5604. *
  5605. *---------------------------------------------------------------------*/
  5606. static void FPT_Wait1Second(u32 p_port)
  5607. {
  5608. unsigned char i;
  5609. for (i = 0; i < 4; i++) {
  5610. FPT_Wait(p_port, TO_250ms);
  5611. if ((RD_HARPOON(p_port + hp_scsictrl_0) & SCSI_RST))
  5612. break;
  5613. if ((RDW_HARPOON((p_port + hp_intstat)) & SCAM_SEL))
  5614. break;
  5615. }
  5616. }
  5617. /*---------------------------------------------------------------------
  5618. *
  5619. * Function: FPT_Wait
  5620. *
  5621. * Description: Wait the desired delay.
  5622. *
  5623. *---------------------------------------------------------------------*/
  5624. static void FPT_Wait(u32 p_port, unsigned char p_delay)
  5625. {
  5626. unsigned char old_timer;
  5627. unsigned char green_flag;
  5628. old_timer = RD_HARPOON(p_port + hp_seltimeout);
  5629. green_flag = RD_HARPOON(p_port + hp_clkctrl_0);
  5630. WR_HARPOON(p_port + hp_clkctrl_0, CLKCTRL_DEFAULT);
  5631. WR_HARPOON(p_port + hp_seltimeout, p_delay);
  5632. WRW_HARPOON((p_port + hp_intstat), TIMEOUT);
  5633. WRW_HARPOON((p_port + hp_intena), (FPT_default_intena & ~TIMEOUT));
  5634. WR_HARPOON(p_port + hp_portctrl_0,
  5635. (RD_HARPOON(p_port + hp_portctrl_0) | START_TO));
  5636. while (!(RDW_HARPOON((p_port + hp_intstat)) & TIMEOUT)) {
  5637. if ((RD_HARPOON(p_port + hp_scsictrl_0) & SCSI_RST))
  5638. break;
  5639. if ((RDW_HARPOON((p_port + hp_intstat)) & SCAM_SEL))
  5640. break;
  5641. }
  5642. WR_HARPOON(p_port + hp_portctrl_0,
  5643. (RD_HARPOON(p_port + hp_portctrl_0) & ~START_TO));
  5644. WRW_HARPOON((p_port + hp_intstat), TIMEOUT);
  5645. WRW_HARPOON((p_port + hp_intena), FPT_default_intena);
  5646. WR_HARPOON(p_port + hp_clkctrl_0, green_flag);
  5647. WR_HARPOON(p_port + hp_seltimeout, old_timer);
  5648. }
  5649. /*---------------------------------------------------------------------
  5650. *
  5651. * Function: Enable/Disable Write to EEPROM
  5652. *
  5653. * Description: The EEPROM must first be enabled for writes
  5654. * A total of 9 clocks are needed.
  5655. *
  5656. *---------------------------------------------------------------------*/
  5657. static void FPT_utilEEWriteOnOff(u32 p_port, unsigned char p_mode)
  5658. {
  5659. unsigned char ee_value;
  5660. ee_value =
  5661. (unsigned char)(RD_HARPOON(p_port + hp_ee_ctrl) &
  5662. (EXT_ARB_ACK | SCSI_TERM_ENA_H));
  5663. if (p_mode)
  5664. FPT_utilEESendCmdAddr(p_port, EWEN, EWEN_ADDR);
  5665. else
  5666. FPT_utilEESendCmdAddr(p_port, EWDS, EWDS_ADDR);
  5667. WR_HARPOON(p_port + hp_ee_ctrl, (ee_value | SEE_MS)); /*Turn off CS */
  5668. WR_HARPOON(p_port + hp_ee_ctrl, ee_value); /*Turn off Master Select */
  5669. }
  5670. /*---------------------------------------------------------------------
  5671. *
  5672. * Function: Write EEPROM
  5673. *
  5674. * Description: Write a word to the EEPROM at the specified
  5675. * address.
  5676. *
  5677. *---------------------------------------------------------------------*/
  5678. static void FPT_utilEEWrite(u32 p_port, unsigned short ee_data,
  5679. unsigned short ee_addr)
  5680. {
  5681. unsigned char ee_value;
  5682. unsigned short i;
  5683. ee_value =
  5684. (unsigned
  5685. char)((RD_HARPOON(p_port + hp_ee_ctrl) &
  5686. (EXT_ARB_ACK | SCSI_TERM_ENA_H)) | (SEE_MS | SEE_CS));
  5687. FPT_utilEESendCmdAddr(p_port, EE_WRITE, ee_addr);
  5688. ee_value |= (SEE_MS + SEE_CS);
  5689. for (i = 0x8000; i != 0; i >>= 1) {
  5690. if (i & ee_data)
  5691. ee_value |= SEE_DO;
  5692. else
  5693. ee_value &= ~SEE_DO;
  5694. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5695. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5696. ee_value |= SEE_CLK; /* Clock data! */
  5697. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5698. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5699. ee_value &= ~SEE_CLK;
  5700. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5701. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5702. }
  5703. ee_value &= (EXT_ARB_ACK | SCSI_TERM_ENA_H);
  5704. WR_HARPOON(p_port + hp_ee_ctrl, (ee_value | SEE_MS));
  5705. FPT_Wait(p_port, TO_10ms);
  5706. WR_HARPOON(p_port + hp_ee_ctrl, (ee_value | SEE_MS | SEE_CS)); /* Set CS to EEPROM */
  5707. WR_HARPOON(p_port + hp_ee_ctrl, (ee_value | SEE_MS)); /* Turn off CS */
  5708. WR_HARPOON(p_port + hp_ee_ctrl, ee_value); /* Turn off Master Select */
  5709. }
  5710. /*---------------------------------------------------------------------
  5711. *
  5712. * Function: Read EEPROM
  5713. *
  5714. * Description: Read a word from the EEPROM at the desired
  5715. * address.
  5716. *
  5717. *---------------------------------------------------------------------*/
  5718. static unsigned short FPT_utilEERead(u32 p_port,
  5719. unsigned short ee_addr)
  5720. {
  5721. unsigned short i, ee_data1, ee_data2;
  5722. i = 0;
  5723. ee_data1 = FPT_utilEEReadOrg(p_port, ee_addr);
  5724. do {
  5725. ee_data2 = FPT_utilEEReadOrg(p_port, ee_addr);
  5726. if (ee_data1 == ee_data2)
  5727. return ee_data1;
  5728. ee_data1 = ee_data2;
  5729. i++;
  5730. } while (i < 4);
  5731. return ee_data1;
  5732. }
  5733. /*---------------------------------------------------------------------
  5734. *
  5735. * Function: Read EEPROM Original
  5736. *
  5737. * Description: Read a word from the EEPROM at the desired
  5738. * address.
  5739. *
  5740. *---------------------------------------------------------------------*/
  5741. static unsigned short FPT_utilEEReadOrg(u32 p_port, unsigned short ee_addr)
  5742. {
  5743. unsigned char ee_value;
  5744. unsigned short i, ee_data;
  5745. ee_value =
  5746. (unsigned
  5747. char)((RD_HARPOON(p_port + hp_ee_ctrl) &
  5748. (EXT_ARB_ACK | SCSI_TERM_ENA_H)) | (SEE_MS | SEE_CS));
  5749. FPT_utilEESendCmdAddr(p_port, EE_READ, ee_addr);
  5750. ee_value |= (SEE_MS + SEE_CS);
  5751. ee_data = 0;
  5752. for (i = 1; i <= 16; i++) {
  5753. ee_value |= SEE_CLK; /* Clock data! */
  5754. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5755. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5756. ee_value &= ~SEE_CLK;
  5757. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5758. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5759. ee_data <<= 1;
  5760. if (RD_HARPOON(p_port + hp_ee_ctrl) & SEE_DI)
  5761. ee_data |= 1;
  5762. }
  5763. ee_value &= ~(SEE_MS + SEE_CS);
  5764. WR_HARPOON(p_port + hp_ee_ctrl, (ee_value | SEE_MS)); /*Turn off CS */
  5765. WR_HARPOON(p_port + hp_ee_ctrl, ee_value); /*Turn off Master Select */
  5766. return ee_data;
  5767. }
  5768. /*---------------------------------------------------------------------
  5769. *
  5770. * Function: Send EE command and Address to the EEPROM
  5771. *
  5772. * Description: Transfers the correct command and sends the address
  5773. * to the eeprom.
  5774. *
  5775. *---------------------------------------------------------------------*/
  5776. static void FPT_utilEESendCmdAddr(u32 p_port, unsigned char ee_cmd,
  5777. unsigned short ee_addr)
  5778. {
  5779. unsigned char ee_value;
  5780. unsigned char narrow_flg;
  5781. unsigned short i;
  5782. narrow_flg =
  5783. (unsigned char)(RD_HARPOON(p_port + hp_page_ctrl) &
  5784. NARROW_SCSI_CARD);
  5785. ee_value = SEE_MS;
  5786. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5787. ee_value |= SEE_CS; /* Set CS to EEPROM */
  5788. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5789. for (i = 0x04; i != 0; i >>= 1) {
  5790. if (i & ee_cmd)
  5791. ee_value |= SEE_DO;
  5792. else
  5793. ee_value &= ~SEE_DO;
  5794. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5795. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5796. ee_value |= SEE_CLK; /* Clock data! */
  5797. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5798. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5799. ee_value &= ~SEE_CLK;
  5800. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5801. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5802. }
  5803. if (narrow_flg)
  5804. i = 0x0080;
  5805. else
  5806. i = 0x0200;
  5807. while (i != 0) {
  5808. if (i & ee_addr)
  5809. ee_value |= SEE_DO;
  5810. else
  5811. ee_value &= ~SEE_DO;
  5812. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5813. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5814. ee_value |= SEE_CLK; /* Clock data! */
  5815. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5816. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5817. ee_value &= ~SEE_CLK;
  5818. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5819. WR_HARPOON(p_port + hp_ee_ctrl, ee_value);
  5820. i >>= 1;
  5821. }
  5822. }
  5823. static unsigned short FPT_CalcCrc16(unsigned char buffer[])
  5824. {
  5825. unsigned short crc = 0;
  5826. int i, j;
  5827. unsigned short ch;
  5828. for (i = 0; i < ID_STRING_LENGTH; i++) {
  5829. ch = (unsigned short)buffer[i];
  5830. for (j = 0; j < 8; j++) {
  5831. if ((crc ^ ch) & 1)
  5832. crc = (crc >> 1) ^ CRCMASK;
  5833. else
  5834. crc >>= 1;
  5835. ch >>= 1;
  5836. }
  5837. }
  5838. return crc;
  5839. }
  5840. static unsigned char FPT_CalcLrc(unsigned char buffer[])
  5841. {
  5842. int i;
  5843. unsigned char lrc;
  5844. lrc = 0;
  5845. for (i = 0; i < ID_STRING_LENGTH; i++)
  5846. lrc ^= buffer[i];
  5847. return lrc;
  5848. }
  5849. /*
  5850. The following inline definitions avoid type conflicts.
  5851. */
  5852. static inline unsigned char
  5853. FlashPoint__ProbeHostAdapter(struct fpoint_info *FlashPointInfo)
  5854. {
  5855. return FlashPoint_ProbeHostAdapter((struct sccb_mgr_info *)
  5856. FlashPointInfo);
  5857. }
  5858. static inline void *
  5859. FlashPoint__HardwareResetHostAdapter(struct fpoint_info *FlashPointInfo)
  5860. {
  5861. return FlashPoint_HardwareResetHostAdapter((struct sccb_mgr_info *)
  5862. FlashPointInfo);
  5863. }
  5864. static inline void
  5865. FlashPoint__ReleaseHostAdapter(void *CardHandle)
  5866. {
  5867. FlashPoint_ReleaseHostAdapter(CardHandle);
  5868. }
  5869. static inline void
  5870. FlashPoint__StartCCB(void *CardHandle, struct blogic_ccb *CCB)
  5871. {
  5872. FlashPoint_StartCCB(CardHandle, (struct sccb *)CCB);
  5873. }
  5874. static inline void
  5875. FlashPoint__AbortCCB(void *CardHandle, struct blogic_ccb *CCB)
  5876. {
  5877. FlashPoint_AbortCCB(CardHandle, (struct sccb *)CCB);
  5878. }
  5879. static inline bool
  5880. FlashPoint__InterruptPending(void *CardHandle)
  5881. {
  5882. return FlashPoint_InterruptPending(CardHandle);
  5883. }
  5884. static inline int
  5885. FlashPoint__HandleInterrupt(void *CardHandle)
  5886. {
  5887. return FlashPoint_HandleInterrupt(CardHandle);
  5888. }
  5889. #define FlashPoint_ProbeHostAdapter FlashPoint__ProbeHostAdapter
  5890. #define FlashPoint_HardwareResetHostAdapter FlashPoint__HardwareResetHostAdapter
  5891. #define FlashPoint_ReleaseHostAdapter FlashPoint__ReleaseHostAdapter
  5892. #define FlashPoint_StartCCB FlashPoint__StartCCB
  5893. #define FlashPoint_AbortCCB FlashPoint__AbortCCB
  5894. #define FlashPoint_InterruptPending FlashPoint__InterruptPending
  5895. #define FlashPoint_HandleInterrupt FlashPoint__HandleInterrupt
  5896. #else /* !CONFIG_SCSI_FLASHPOINT */
  5897. /*
  5898. Define prototypes for the FlashPoint SCCB Manager Functions.
  5899. */
  5900. extern unsigned char FlashPoint_ProbeHostAdapter(struct fpoint_info *);
  5901. extern void *FlashPoint_HardwareResetHostAdapter(struct fpoint_info *);
  5902. extern void FlashPoint_StartCCB(void *, struct blogic_ccb *);
  5903. extern int FlashPoint_AbortCCB(void *, struct blogic_ccb *);
  5904. extern bool FlashPoint_InterruptPending(void *);
  5905. extern int FlashPoint_HandleInterrupt(void *);
  5906. extern void FlashPoint_ReleaseHostAdapter(void *);
  5907. #endif /* CONFIG_SCSI_FLASHPOINT */