DbgExprEvaluator.cpp 232 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517251825192520252125222523252425252526252725282529253025312532253325342535253625372538253925402541254225432544254525462547254825492550255125522553255425552556255725582559256025612562256325642565256625672568256925702571257225732574257525762577257825792580258125822583258425852586258725882589259025912592259325942595259625972598259926002601260226032604260526062607260826092610261126122613261426152616261726182619262026212622262326242625262626272628262926302631263226332634263526362637263826392640264126422643264426452646264726482649265026512652265326542655265626572658265926602661266226632664266526662667266826692670267126722673267426752676267726782679268026812682268326842685268626872688268926902691269226932694269526962697269826992700270127022703270427052706270727082709271027112712271327142715271627172718271927202721272227232724272527262727272827292730273127322733273427352736273727382739274027412742274327442745274627472748274927502751275227532754275527562757275827592760276127622763276427652766276727682769277027712772277327742775277627772778277927802781278227832784278527862787278827892790279127922793279427952796279727982799280028012802280328042805280628072808280928102811281228132814281528162817281828192820282128222823282428252826282728282829283028312832283328342835283628372838283928402841284228432844284528462847284828492850285128522853285428552856285728582859286028612862286328642865286628672868286928702871287228732874287528762877287828792880288128822883288428852886288728882889289028912892289328942895289628972898289929002901290229032904290529062907290829092910291129122913291429152916291729182919292029212922292329242925292629272928292929302931293229332934293529362937293829392940294129422943294429452946294729482949295029512952295329542955295629572958295929602961296229632964296529662967296829692970297129722973297429752976297729782979298029812982298329842985298629872988298929902991299229932994299529962997299829993000300130023003300430053006300730083009301030113012301330143015301630173018301930203021302230233024302530263027302830293030303130323033303430353036303730383039304030413042304330443045304630473048304930503051305230533054305530563057305830593060306130623063306430653066306730683069307030713072307330743075307630773078307930803081308230833084308530863087308830893090309130923093309430953096309730983099310031013102310331043105310631073108310931103111311231133114311531163117311831193120312131223123312431253126312731283129313031313132313331343135313631373138313931403141314231433144314531463147314831493150315131523153315431553156315731583159316031613162316331643165316631673168316931703171317231733174317531763177317831793180318131823183318431853186318731883189319031913192319331943195319631973198319932003201320232033204320532063207320832093210321132123213321432153216321732183219322032213222322332243225322632273228322932303231323232333234323532363237323832393240324132423243324432453246324732483249325032513252325332543255325632573258325932603261326232633264326532663267326832693270327132723273327432753276327732783279328032813282328332843285328632873288328932903291329232933294329532963297329832993300330133023303330433053306330733083309331033113312331333143315331633173318331933203321332233233324332533263327332833293330333133323333333433353336333733383339334033413342334333443345334633473348334933503351335233533354335533563357335833593360336133623363336433653366336733683369337033713372337333743375337633773378337933803381338233833384338533863387338833893390339133923393339433953396339733983399340034013402340334043405340634073408340934103411341234133414341534163417341834193420342134223423342434253426342734283429343034313432343334343435343634373438343934403441344234433444344534463447344834493450345134523453345434553456345734583459346034613462346334643465346634673468346934703471347234733474347534763477347834793480348134823483348434853486348734883489349034913492349334943495349634973498349935003501350235033504350535063507350835093510351135123513351435153516351735183519352035213522352335243525352635273528352935303531353235333534353535363537353835393540354135423543354435453546354735483549355035513552355335543555355635573558355935603561356235633564356535663567356835693570357135723573357435753576357735783579358035813582358335843585358635873588358935903591359235933594359535963597359835993600360136023603360436053606360736083609361036113612361336143615361636173618361936203621362236233624362536263627362836293630363136323633363436353636363736383639364036413642364336443645364636473648364936503651365236533654365536563657365836593660366136623663366436653666366736683669367036713672367336743675367636773678367936803681368236833684368536863687368836893690369136923693369436953696369736983699370037013702370337043705370637073708370937103711371237133714371537163717371837193720372137223723372437253726372737283729373037313732373337343735373637373738373937403741374237433744374537463747374837493750375137523753375437553756375737583759376037613762376337643765376637673768376937703771377237733774377537763777377837793780378137823783378437853786378737883789379037913792379337943795379637973798379938003801380238033804380538063807380838093810381138123813381438153816381738183819382038213822382338243825382638273828382938303831383238333834383538363837383838393840384138423843384438453846384738483849385038513852385338543855385638573858385938603861386238633864386538663867386838693870387138723873387438753876387738783879388038813882388338843885388638873888388938903891389238933894389538963897389838993900390139023903390439053906390739083909391039113912391339143915391639173918391939203921392239233924392539263927392839293930393139323933393439353936393739383939394039413942394339443945394639473948394939503951395239533954395539563957395839593960396139623963396439653966396739683969397039713972397339743975397639773978397939803981398239833984398539863987398839893990399139923993399439953996399739983999400040014002400340044005400640074008400940104011401240134014401540164017401840194020402140224023402440254026402740284029403040314032403340344035403640374038403940404041404240434044404540464047404840494050405140524053405440554056405740584059406040614062406340644065406640674068406940704071407240734074407540764077407840794080408140824083408440854086408740884089409040914092409340944095409640974098409941004101410241034104410541064107410841094110411141124113411441154116411741184119412041214122412341244125412641274128412941304131413241334134413541364137413841394140414141424143414441454146414741484149415041514152415341544155415641574158415941604161416241634164416541664167416841694170417141724173417441754176417741784179418041814182418341844185418641874188418941904191419241934194419541964197419841994200420142024203420442054206420742084209421042114212421342144215421642174218421942204221422242234224422542264227422842294230423142324233423442354236423742384239424042414242424342444245424642474248424942504251425242534254425542564257425842594260426142624263426442654266426742684269427042714272427342744275427642774278427942804281428242834284428542864287428842894290429142924293429442954296429742984299430043014302430343044305430643074308430943104311431243134314431543164317431843194320432143224323432443254326432743284329433043314332433343344335433643374338433943404341434243434344434543464347434843494350435143524353435443554356435743584359436043614362436343644365436643674368436943704371437243734374437543764377437843794380438143824383438443854386438743884389439043914392439343944395439643974398439944004401440244034404440544064407440844094410441144124413441444154416441744184419442044214422442344244425442644274428442944304431443244334434443544364437443844394440444144424443444444454446444744484449445044514452445344544455445644574458445944604461446244634464446544664467446844694470447144724473447444754476447744784479448044814482448344844485448644874488448944904491449244934494449544964497449844994500450145024503450445054506450745084509451045114512451345144515451645174518451945204521452245234524452545264527452845294530453145324533453445354536453745384539454045414542454345444545454645474548454945504551455245534554455545564557455845594560456145624563456445654566456745684569457045714572457345744575457645774578457945804581458245834584458545864587458845894590459145924593459445954596459745984599460046014602460346044605460646074608460946104611461246134614461546164617461846194620462146224623462446254626462746284629463046314632463346344635463646374638463946404641464246434644464546464647464846494650465146524653465446554656465746584659466046614662466346644665466646674668466946704671467246734674467546764677467846794680468146824683468446854686468746884689469046914692469346944695469646974698469947004701470247034704470547064707470847094710471147124713471447154716471747184719472047214722472347244725472647274728472947304731473247334734473547364737473847394740474147424743474447454746474747484749475047514752475347544755475647574758475947604761476247634764476547664767476847694770477147724773477447754776477747784779478047814782478347844785478647874788478947904791479247934794479547964797479847994800480148024803480448054806480748084809481048114812481348144815481648174818481948204821482248234824482548264827482848294830483148324833483448354836483748384839484048414842484348444845484648474848484948504851485248534854485548564857485848594860486148624863486448654866486748684869487048714872487348744875487648774878487948804881488248834884488548864887488848894890489148924893489448954896489748984899490049014902490349044905490649074908490949104911491249134914491549164917491849194920492149224923492449254926492749284929493049314932493349344935493649374938493949404941494249434944494549464947494849494950495149524953495449554956495749584959496049614962496349644965496649674968496949704971497249734974497549764977497849794980498149824983498449854986498749884989499049914992499349944995499649974998499950005001500250035004500550065007500850095010501150125013501450155016501750185019502050215022502350245025502650275028502950305031503250335034503550365037503850395040504150425043504450455046504750485049505050515052505350545055505650575058505950605061506250635064506550665067506850695070507150725073507450755076507750785079508050815082508350845085508650875088508950905091509250935094509550965097509850995100510151025103510451055106510751085109511051115112511351145115511651175118511951205121512251235124512551265127512851295130513151325133513451355136513751385139514051415142514351445145514651475148514951505151515251535154515551565157515851595160516151625163516451655166516751685169517051715172517351745175517651775178517951805181518251835184518551865187518851895190519151925193519451955196519751985199520052015202520352045205520652075208520952105211521252135214521552165217521852195220522152225223522452255226522752285229523052315232523352345235523652375238523952405241524252435244524552465247524852495250525152525253525452555256525752585259526052615262526352645265526652675268526952705271527252735274527552765277527852795280528152825283528452855286528752885289529052915292529352945295529652975298529953005301530253035304530553065307530853095310531153125313531453155316531753185319532053215322532353245325532653275328532953305331533253335334533553365337533853395340534153425343534453455346534753485349535053515352535353545355535653575358535953605361536253635364536553665367536853695370537153725373537453755376537753785379538053815382538353845385538653875388538953905391539253935394539553965397539853995400540154025403540454055406540754085409541054115412541354145415541654175418541954205421542254235424542554265427542854295430543154325433543454355436543754385439544054415442544354445445544654475448544954505451545254535454545554565457545854595460546154625463546454655466546754685469547054715472547354745475547654775478547954805481548254835484548554865487548854895490549154925493549454955496549754985499550055015502550355045505550655075508550955105511551255135514551555165517551855195520552155225523552455255526552755285529553055315532553355345535553655375538553955405541554255435544554555465547554855495550555155525553555455555556555755585559556055615562556355645565556655675568556955705571557255735574557555765577557855795580558155825583558455855586558755885589559055915592559355945595559655975598559956005601560256035604560556065607560856095610561156125613561456155616561756185619562056215622562356245625562656275628562956305631563256335634563556365637563856395640564156425643564456455646564756485649565056515652565356545655565656575658565956605661566256635664566556665667566856695670567156725673567456755676567756785679568056815682568356845685568656875688568956905691569256935694569556965697569856995700570157025703570457055706570757085709571057115712571357145715571657175718571957205721572257235724572557265727572857295730573157325733573457355736573757385739574057415742574357445745574657475748574957505751575257535754575557565757575857595760576157625763576457655766576757685769577057715772577357745775577657775778577957805781578257835784578557865787578857895790579157925793579457955796579757985799580058015802580358045805580658075808580958105811581258135814581558165817581858195820582158225823582458255826582758285829583058315832583358345835583658375838583958405841584258435844584558465847584858495850585158525853585458555856585758585859586058615862586358645865586658675868586958705871587258735874587558765877587858795880588158825883588458855886588758885889589058915892589358945895589658975898589959005901590259035904590559065907590859095910591159125913591459155916591759185919592059215922592359245925592659275928592959305931593259335934593559365937593859395940594159425943594459455946594759485949595059515952595359545955595659575958595959605961596259635964596559665967596859695970597159725973597459755976597759785979598059815982598359845985598659875988598959905991599259935994599559965997599859996000600160026003600460056006600760086009601060116012601360146015601660176018601960206021602260236024602560266027602860296030603160326033603460356036603760386039604060416042604360446045604660476048604960506051605260536054605560566057605860596060606160626063606460656066606760686069607060716072607360746075607660776078607960806081608260836084608560866087608860896090609160926093609460956096609760986099610061016102610361046105610661076108610961106111611261136114611561166117611861196120612161226123612461256126612761286129613061316132613361346135613661376138613961406141614261436144614561466147614861496150615161526153615461556156615761586159616061616162616361646165616661676168616961706171617261736174617561766177617861796180618161826183618461856186618761886189619061916192619361946195619661976198619962006201620262036204620562066207620862096210621162126213621462156216621762186219622062216222622362246225622662276228622962306231623262336234623562366237623862396240624162426243624462456246624762486249625062516252625362546255625662576258625962606261626262636264626562666267626862696270627162726273627462756276627762786279628062816282628362846285628662876288628962906291629262936294629562966297629862996300630163026303630463056306630763086309631063116312631363146315631663176318631963206321632263236324632563266327632863296330633163326333633463356336633763386339634063416342634363446345634663476348634963506351635263536354635563566357635863596360636163626363636463656366636763686369637063716372637363746375637663776378637963806381638263836384638563866387638863896390639163926393639463956396639763986399640064016402640364046405640664076408640964106411641264136414641564166417641864196420642164226423642464256426642764286429643064316432643364346435643664376438643964406441644264436444644564466447644864496450645164526453645464556456645764586459646064616462646364646465646664676468646964706471647264736474647564766477647864796480648164826483648464856486648764886489649064916492649364946495649664976498649965006501650265036504650565066507650865096510651165126513651465156516651765186519652065216522652365246525652665276528652965306531653265336534653565366537653865396540654165426543654465456546654765486549655065516552655365546555655665576558655965606561656265636564656565666567656865696570657165726573657465756576657765786579658065816582658365846585658665876588658965906591659265936594659565966597659865996600660166026603660466056606660766086609661066116612661366146615661666176618661966206621662266236624662566266627662866296630663166326633663466356636663766386639664066416642664366446645664666476648664966506651665266536654665566566657665866596660666166626663666466656666666766686669667066716672667366746675667666776678667966806681668266836684668566866687668866896690669166926693669466956696669766986699670067016702670367046705670667076708670967106711671267136714671567166717671867196720672167226723672467256726672767286729673067316732673367346735673667376738673967406741674267436744674567466747674867496750675167526753675467556756675767586759676067616762676367646765676667676768676967706771677267736774677567766777677867796780678167826783678467856786678767886789679067916792679367946795679667976798679968006801680268036804680568066807680868096810681168126813681468156816681768186819682068216822682368246825682668276828682968306831683268336834683568366837683868396840684168426843684468456846684768486849685068516852685368546855685668576858685968606861686268636864686568666867686868696870687168726873687468756876687768786879688068816882688368846885688668876888688968906891689268936894689568966897689868996900690169026903690469056906690769086909691069116912691369146915691669176918691969206921692269236924692569266927692869296930693169326933693469356936693769386939694069416942694369446945694669476948694969506951695269536954695569566957695869596960696169626963696469656966696769686969697069716972697369746975697669776978697969806981698269836984698569866987698869896990699169926993699469956996699769986999700070017002700370047005700670077008700970107011701270137014701570167017701870197020702170227023702470257026702770287029703070317032703370347035703670377038703970407041704270437044704570467047704870497050705170527053705470557056705770587059706070617062706370647065706670677068706970707071707270737074707570767077707870797080708170827083708470857086708770887089709070917092709370947095709670977098709971007101710271037104710571067107710871097110711171127113711471157116711771187119712071217122712371247125712671277128712971307131713271337134713571367137713871397140714171427143714471457146714771487149715071517152715371547155715671577158715971607161716271637164716571667167716871697170717171727173717471757176717771787179718071817182718371847185718671877188718971907191719271937194719571967197719871997200720172027203720472057206720772087209721072117212721372147215721672177218721972207221722272237224722572267227722872297230723172327233723472357236723772387239724072417242724372447245724672477248724972507251725272537254725572567257725872597260726172627263726472657266726772687269727072717272727372747275727672777278727972807281728272837284728572867287728872897290729172927293729472957296729772987299730073017302730373047305730673077308730973107311731273137314731573167317731873197320732173227323732473257326732773287329733073317332733373347335733673377338733973407341734273437344734573467347734873497350735173527353735473557356735773587359736073617362736373647365736673677368736973707371737273737374737573767377737873797380738173827383738473857386738773887389739073917392739373947395739673977398739974007401740274037404740574067407740874097410741174127413741474157416741774187419742074217422742374247425742674277428742974307431743274337434743574367437743874397440744174427443744474457446744774487449745074517452745374547455745674577458745974607461746274637464746574667467746874697470747174727473747474757476747774787479748074817482748374847485748674877488748974907491749274937494749574967497749874997500750175027503750475057506750775087509751075117512751375147515751675177518751975207521752275237524752575267527752875297530753175327533753475357536753775387539754075417542754375447545754675477548754975507551755275537554755575567557755875597560756175627563756475657566756775687569757075717572757375747575757675777578757975807581758275837584758575867587758875897590759175927593759475957596759775987599760076017602760376047605760676077608760976107611761276137614761576167617761876197620762176227623762476257626762776287629763076317632763376347635763676377638763976407641764276437644764576467647764876497650765176527653765476557656765776587659766076617662766376647665766676677668766976707671767276737674767576767677767876797680768176827683768476857686768776887689769076917692769376947695769676977698769977007701770277037704770577067707770877097710771177127713771477157716771777187719772077217722772377247725772677277728772977307731773277337734773577367737773877397740774177427743774477457746774777487749775077517752775377547755775677577758775977607761776277637764776577667767776877697770777177727773777477757776777777787779778077817782778377847785778677877788778977907791779277937794779577967797779877997800780178027803780478057806780778087809781078117812781378147815781678177818781978207821782278237824782578267827782878297830783178327833783478357836783778387839784078417842784378447845784678477848784978507851785278537854785578567857785878597860786178627863786478657866786778687869787078717872787378747875787678777878787978807881788278837884788578867887788878897890789178927893789478957896789778987899790079017902790379047905790679077908790979107911791279137914791579167917791879197920792179227923792479257926792779287929793079317932793379347935793679377938793979407941794279437944794579467947794879497950795179527953795479557956795779587959796079617962796379647965796679677968796979707971797279737974797579767977797879797980798179827983798479857986798779887989799079917992799379947995799679977998799980008001800280038004800580068007800880098010801180128013801480158016801780188019802080218022802380248025802680278028802980308031803280338034803580368037803880398040804180428043804480458046804780488049805080518052805380548055805680578058805980608061806280638064806580668067806880698070807180728073807480758076807780788079808080818082808380848085808680878088808980908091809280938094809580968097809880998100810181028103810481058106810781088109811081118112811381148115811681178118811981208121812281238124812581268127812881298130813181328133813481358136813781388139814081418142814381448145814681478148814981508151815281538154815581568157815881598160816181628163816481658166816781688169817081718172817381748175817681778178817981808181818281838184818581868187818881898190819181928193819481958196819781988199820082018202820382048205820682078208820982108211821282138214821582168217821882198220822182228223822482258226822782288229823082318232823382348235823682378238823982408241824282438244824582468247824882498250825182528253825482558256825782588259826082618262826382648265826682678268826982708271827282738274827582768277827882798280828182828283828482858286828782888289829082918292829382948295829682978298829983008301830283038304830583068307830883098310831183128313831483158316831783188319832083218322832383248325832683278328832983308331833283338334833583368337833883398340834183428343834483458346834783488349835083518352835383548355835683578358835983608361836283638364836583668367836883698370837183728373837483758376837783788379838083818382838383848385838683878388838983908391839283938394839583968397839883998400840184028403840484058406840784088409841084118412841384148415841684178418841984208421842284238424842584268427842884298430843184328433843484358436843784388439844084418442844384448445844684478448844984508451845284538454845584568457845884598460846184628463846484658466846784688469847084718472847384748475
  1. #include "DbgExprEvaluator.h"
  2. #include "WinDebugger.h"
  3. #include "Compiler/BfUtil.h"
  4. #include "Compiler/BfSystem.h"
  5. #include "Compiler/BfParser.h"
  6. #include "Compiler/BfReducer.h"
  7. #include "Compiler/BfPrinter.h"
  8. #include "Compiler/BfDemangler.h"
  9. #include "DWARFInfo.h"
  10. #include "DebugManager.h"
  11. #include "DebugVisualizers.h"
  12. #include "BeefySysLib/util/BeefPerf.h"
  13. #include "BeefySysLib/util/StackHelper.h"
  14. #include "BeefySysLib/util/AllocDebug.h"
  15. USING_NS_BF_DBG;
  16. using namespace llvm;
  17. //////////////////////////////////////////////////////////////////////////
  18. DwMethodMatcher::DwMethodMatcher(BfAstNode* targetSrc, DbgExprEvaluator* exprEvaluator, const StringImpl& methodName, SizedArrayImpl<DbgTypedValue>& arguments, BfSizedArray<ASTREF(BfAstNode*)>* methodGenericArguments) :
  19. mArguments(arguments)
  20. {
  21. mTargetSrc = targetSrc;
  22. mExprEvaluator = exprEvaluator;
  23. mMethodName = methodName;
  24. mArguments = arguments;
  25. mBestMethodDef = NULL;
  26. mBackupMethodDef = NULL;
  27. mBestMethodTypeInstance = NULL;
  28. mExplicitInterfaceCheck = NULL;
  29. mHadExplicitGenericArguments = false;
  30. mTargetIsConst = false;
  31. if (methodGenericArguments != NULL)
  32. {
  33. for (auto genericArg : *methodGenericArguments)
  34. {
  35. if (genericArg == NULL)
  36. return;
  37. auto genericArgType = mExprEvaluator->ResolveTypeRef(genericArg);
  38. if (genericArgType == NULL)
  39. return;
  40. mBestMethodGenericArguments.push_back(genericArgType);
  41. //mBestMethodGenericArgumentSrcs.push_back(genericArg);
  42. }
  43. mHadExplicitGenericArguments = true;
  44. }
  45. }
  46. /*bool DwMethodMatcher::InferGenericArgument(DbgType* argType, DbgType* wantType)
  47. {
  48. if (argType == NULL)
  49. return false;
  50. if (wantType->IsGenericParam())
  51. {
  52. auto wantGenericParam = (BfGenericParamType*)wantType;
  53. if (wantGenericParam->mGenericParamKind == BfGenericParamKind_Method)
  54. {
  55. auto prevGenericMethodArg = mCheckMethodGenericArguments[wantGenericParam->mGenericParamIdx];
  56. if (prevGenericMethodArg == NULL)
  57. {
  58. mCheckMethodGenericArguments[wantGenericParam->mGenericParamIdx] = argType;
  59. return true;
  60. }
  61. // Prev is already best
  62. if (mModule->CanCast(DbgTypedValue(NULL, argType), prevGenericMethodArg))
  63. return true;
  64. // New best?
  65. if (mModule->CanCast(DbgTypedValue(NULL, prevGenericMethodArg), argType))
  66. {
  67. mCheckMethodGenericArguments[wantGenericParam->mGenericParamIdx] = argType;
  68. return true;
  69. }
  70. // No implicit conversion, FAIL!
  71. mCheckMethodGenericArguments[wantGenericParam->mGenericParamIdx] = NULL;
  72. return false;
  73. }
  74. return true;
  75. }
  76. if (wantType->IsGenericTypeInstance())
  77. {
  78. if (!argType->IsGenericTypeInstance())
  79. return true;
  80. auto wantGenericType = (BfTypeInstance*)wantType;
  81. auto argGenericType = (BfTypeInstance*)argType;
  82. if (argGenericType->mTypeDef != wantGenericType->mTypeDef)
  83. return true;
  84. for (int genericArgIdx = 0; genericArgIdx < (int)argGenericType->mTypeGenericArguments.size(); genericArgIdx++)
  85. InferGenericArgument(argGenericType->mTypeGenericArguments[genericArgIdx], wantGenericType->mTypeGenericArguments[genericArgIdx]);
  86. return true;
  87. }
  88. if (wantType->IsRef())
  89. {
  90. if (!argType->IsRef())
  91. return true;
  92. auto wantRefType = (BfRefType*)wantType;
  93. auto argRefType = (BfRefType*)argType;
  94. if (wantRefType->mIsOut != argRefType->mIsOut)
  95. return true;
  96. InferGenericArgument(argRefType->mElementType, wantRefType->mElementType);
  97. return true;
  98. }
  99. if (wantType->IsPointer())
  100. {
  101. if (!argType->IsPointer())
  102. return true;
  103. auto wantPointerType = (BfPointerType*) wantType;
  104. auto argPointerType = (BfPointerType*) argType;
  105. InferGenericArgument(argPointerType->mElementType, wantPointerType->mElementType);
  106. return true;
  107. }
  108. return true;
  109. }*/
  110. void DwMethodMatcher::CompareMethods(DbgSubprogram* prevMethodInstance, DwTypeVector* prevGenericArgumentsSubstitute,
  111. DbgSubprogram* newMethodInstance, DwTypeVector* genericArgumentsSubstitute,
  112. bool* outNewIsBetter, bool* outNewIsWorse, bool allowSpecializeFail)
  113. {
  114. int numUsedParams = 0;
  115. int prevNumUsedParams = 0;
  116. bool usedExtendedForm = false;
  117. bool prevUsedExtendedForm = false;
  118. bool isBetter = false;
  119. bool isWorse = false;
  120. int argIdx = 0;
  121. DbgSubprogram* prevMethodDef = prevMethodInstance;
  122. DbgSubprogram* newMethodDef = newMethodInstance;
  123. #define SET_BETTER_OR_WORSE(lhs, rhs) \
  124. if ((lhs) && !(rhs)) isBetter = true; \
  125. if (!(lhs) && (rhs)) isWorse = true;
  126. int newArgOffset = newMethodInstance->mHasThis ? 1 : 0;
  127. int prevArgOffset = prevMethodInstance->mHasThis ? 1 : 0;
  128. DbgVariable* param = newMethodInstance->mParams.mHead;
  129. if (newMethodInstance->mHasThis)
  130. param = param->mNext;
  131. DbgVariable* prevParam = prevMethodInstance->mParams.mHead;
  132. if (prevMethodInstance->mHasThis)
  133. prevParam = prevParam->mNext;
  134. for (argIdx = 0; argIdx < (int) mArguments.size(); argIdx++)
  135. {
  136. DbgTypedValue arg = mArguments[argIdx];
  137. DbgType* paramType = param->mType;
  138. DbgType* prevParamType = prevParam->mType;
  139. numUsedParams++;
  140. prevNumUsedParams++;
  141. /*if ((genericArgumentsSubstitute != NULL) && (paramType->IsUnspecializedType()))
  142. paramType = mModule->SpecializeMethodType(paramType, *genericArgumentsSubstitute, allowSpecializeFail);
  143. if (prevParamType->IsUnspecializedType())
  144. prevParamType = mModule->SpecializeMethodType(prevParamType, *prevGenericArgumentsSubstitute, allowSpecializeFail);*/
  145. //paramType = paramType->RemoveModifiers();
  146. //prevParamType = prevParamType->RemoveModifiers();
  147. if (paramType != prevParamType)
  148. {
  149. /*if ((paramType->IsGenericParam()) || (prevParamType->IsGenericParam()))
  150. {
  151. BF_ASSERT(allowSpecializeFail);
  152. if (!prevParamType->IsGenericParam())
  153. isBetter = true;
  154. else if (!paramType->IsGenericParam())
  155. isWorse = true;
  156. }
  157. else*/ if ((paramType->IsInteger()) && (prevParamType->IsInteger()))
  158. {
  159. if (paramType == arg.mType)
  160. isBetter = true;
  161. else if (prevParamType == arg.mType)
  162. isWorse = true;
  163. else
  164. {
  165. if (paramType->mSize < prevParamType->mSize)
  166. isBetter = true;
  167. else if (paramType->mSize > prevParamType->mSize)
  168. isWorse = true;
  169. else if (paramType->IsSigned())
  170. isBetter = true;
  171. else
  172. isWorse = true;
  173. }
  174. }
  175. else
  176. {
  177. if (mExprEvaluator->CanCast(DbgTypedValue::GetValueless(paramType), prevParamType))
  178. isBetter = true;
  179. if (mExprEvaluator->CanCast(DbgTypedValue::GetValueless(prevParamType), paramType))
  180. isWorse = true;
  181. }
  182. }
  183. /*if (newMethodDef->mParams[argIdx]->mParamType == BfParamType_Params)
  184. usedExtendedForm = true;
  185. if (prevMethodDef->mParams[argIdx]->mParamType == BfParamType_Params)
  186. prevUsedExtendedForm = true;*/
  187. if ((usedExtendedForm) || (prevUsedExtendedForm))
  188. break;
  189. param = param->mNext;
  190. prevParam = prevParam->mNext;
  191. }
  192. // Check for unused extended params as next param - that still counts as using extended form
  193. /*if ((argIdx < (int) newMethodDef->mParams.size()) && (newMethodDef->mParams[argIdx]->mParamType == BfParamType_Params))
  194. usedExtendedForm = true;
  195. if ((argIdx < (int) prevMethodDef->mParams.size()) && (prevMethodDef->mParams[argIdx]->mParamType == BfParamType_Params))
  196. prevUsedExtendedForm = true;*/
  197. // Non-generic trumps generic
  198. /*if ((!isBetter) && (!isWorse))
  199. {
  200. SET_BETTER_OR_WORSE(newMethodInstance->mMethodGenericArguments.size() == 0, prevMethodInstance->mMethodGenericArguments.size() == 0);
  201. }*/
  202. // Normal form trumps extended form
  203. if ((!isBetter) && (!isWorse))
  204. {
  205. SET_BETTER_OR_WORSE(!usedExtendedForm, !prevUsedExtendedForm);
  206. }
  207. // More used params trumps less params
  208. if ((!isBetter) && (!isWorse))
  209. {
  210. int paramDiff = (int) numUsedParams - (int) prevNumUsedParams;
  211. SET_BETTER_OR_WORSE(paramDiff > 0, paramDiff < 0);
  212. }
  213. // Fewer defaults trumps more defaults
  214. /*if ((!isBetter) && (!isWorse))
  215. {
  216. // Since we know the number of used params is the same (previous check), we infer that the rest are defaults
  217. int paramDiff = (int) newMethodInstance->mParamTypes.size() - (int) prevMethodInstance->mParamTypes.size();
  218. SET_BETTER_OR_WORSE(paramDiff < 0, paramDiff > 0);
  219. }*/
  220. // Check specificity of args
  221. if ((!isBetter) && (!isWorse))
  222. {
  223. param = newMethodInstance->mParams.mHead;
  224. if (newMethodInstance->mHasThis)
  225. param = param->mNext;
  226. prevParam = prevMethodInstance->mParams.mHead;
  227. if (prevMethodInstance->mHasThis)
  228. prevParam = prevParam->mNext;
  229. for (argIdx = 0; argIdx < (int) mArguments.size(); argIdx++)
  230. {
  231. DbgType* paramType = param->mType;
  232. DbgType* prevParamType = prevParam->mType;
  233. //TODO:
  234. //isBetter |= mModule->IsTypeMoreSpecific(paramType, prevParamType);
  235. //isWorse |= mModule->IsTypeMoreSpecific(prevParamType, paramType);
  236. param = param->mNext;
  237. prevParam = prevParam->mNext;
  238. }
  239. }
  240. // Prefer virtual - this helps us bind to a virtual override instead of the concrete method implementation so we can ignore it and
  241. // continue searching through the base types to find the original virtual method
  242. if ((!isBetter) && (!isWorse))
  243. {
  244. SET_BETTER_OR_WORSE(newMethodInstance->mVirtual, prevMethodInstance->mVirtual);
  245. }
  246. if ((!isBetter) && (!isWorse))
  247. {
  248. SET_BETTER_OR_WORSE(newMethodInstance->mBlock.mLowPC != 0, prevMethodInstance->mBlock.mLowPC != 0);
  249. }
  250. if ((!isBetter) && (!isWorse))
  251. {
  252. if ((newMethodInstance->mHasThis) && (prevMethodInstance->mHasThis))
  253. {
  254. SET_BETTER_OR_WORSE(
  255. newMethodInstance->mParams.mHead->mType->IsConst() == mTargetIsConst,
  256. prevMethodInstance->mParams.mHead->mType->IsConst() == mTargetIsConst);
  257. }
  258. }
  259. *outNewIsBetter = isBetter;
  260. *outNewIsWorse = isWorse;
  261. }
  262. bool DwMethodMatcher::CheckMethod(DbgType* typeInstance, DbgSubprogram* checkMethod)
  263. {
  264. bool hadMatch = false;
  265. checkMethod->PopulateSubprogram();
  266. // Never consider overrides - they only get found at original method declaration
  267. /*if ((checkMethod->mVirtual) && (checkMethod->mVTableLoc == -1))
  268. return true;*/
  269. //BfMethodInstance* methodInstance = mModule->GetRawMethodInstanceAtIdx(typeInstance, checkMethod->mIdx);
  270. DbgSubprogram* methodInstance = checkMethod;
  271. DwAutoComplete* autoComplete = mExprEvaluator->mAutoComplete;
  272. if ((autoComplete != NULL) && (autoComplete->mIsCapturingMethodMatchInfo))
  273. {
  274. DwAutoComplete::MethodMatchEntry methodMatchEntry;
  275. methodMatchEntry.mDwSubprogram = methodInstance;
  276. autoComplete->mMethodMatchInfo->mInstanceList.push_back(methodMatchEntry);
  277. }
  278. /*if ((mHadExplicitGenericArguments) && (checkMethod->mGenericParams.size() != mBestMethodGenericArguments.size()))
  279. goto NoMatch;*/
  280. for (auto& checkGenericArgRef : mCheckMethodGenericArguments)
  281. checkGenericArgRef = NULL;
  282. /*mCheckMethodGenericArguments.resize(checkMethod->mGenericParams.size());
  283. for (auto& genericArgRef : mCheckMethodGenericArguments)
  284. genericArgRef = NULL;*/
  285. int argIdx = 0;
  286. int paramIdx = 0;
  287. DbgType* paramsElementType = NULL;
  288. //bool needInferGenericParams = (checkMethod->mGenericParams.size() != 0) && (!mHadExplicitGenericArguments);
  289. DwTypeVector* genericArgumentsSubstitute = NULL;
  290. /*if (mHadExplicitGenericArguments)
  291. genericArgumentsSubstitute = &mBestMethodGenericArguments;
  292. else if (needInferGenericParams)
  293. genericArgumentsSubstitute = &mCheckMethodGenericArguments;
  294. if (needInferGenericParams)
  295. {
  296. for (int argIdx = 0; argIdx < (int)mArguments.size(); argIdx++)
  297. {
  298. if (argIdx >= (int)checkMethod->mParams.size())
  299. break;
  300. auto wantType = methodInstance->mParamTypes[argIdx];
  301. if (wantType->IsUnspecializedType())
  302. {
  303. if (!InferGenericArgument(mArguments[argIdx].mType, wantType))
  304. goto NoMatch;
  305. }
  306. }
  307. for (int checkArgIdx = 0; checkArgIdx < (int) checkMethod->mGenericParams.size(); checkArgIdx++)
  308. if (mCheckMethodGenericArguments[checkArgIdx] == NULL)
  309. goto NoMatch;
  310. }*/
  311. // Iterate through params
  312. int paramOffset = checkMethod->mHasThis ? 1 : 0;
  313. while (true)
  314. {
  315. // Too many arguments
  316. if (paramIdx >= checkMethod->mParams.Size() - paramOffset)
  317. {
  318. break;
  319. }
  320. DbgVariable* paramDef = checkMethod->mParams[paramIdx + paramOffset];
  321. //TODO:
  322. /*if ((paramDef->mParamType == BfParamType_Params) && (paramsElementType == NULL))
  323. {
  324. if (paramIdx >= (int) mArguments.size())
  325. break; // No params
  326. if (!mArguments[argIdx])
  327. goto NoMatch;
  328. // Check to see if we're directly passing the params type (like an int[])
  329. auto paramsArrayType = methodInstance->mParamTypes[paramIdx];
  330. if (mModule->CanCast(mArguments[argIdx], paramsArrayType))
  331. {
  332. argIdx++;
  333. paramIdx++;
  334. break;
  335. }
  336. BF_ASSERT(paramsArrayType->IsArray());
  337. auto arrayType = (BfArrayType*)paramsArrayType;
  338. paramsElementType = arrayType->mTypeGenericArguments[0];
  339. while (argIdx < (int)mArguments.size())
  340. {
  341. if (!mArguments[argIdx])
  342. goto NoMatch;
  343. if (!mModule->CanCast(mArguments[argIdx], paramsElementType))
  344. goto NoMatch;
  345. argIdx++;
  346. }
  347. break;
  348. }*/
  349. if (paramIdx >= (int) mArguments.size())
  350. {
  351. // We have defaults the rest of the way, so that's cool
  352. //TODO:
  353. /*if (paramDef->mParamDeclaration->mInitializer != NULL)
  354. break;*/
  355. // We have unused params left over
  356. goto NoMatch;
  357. }
  358. auto wantType = paramDef->mType;
  359. /*if ((genericArgumentsSubstitute != NULL) && (wantType->IsUnspecializedType()))
  360. wantType = mModule->SpecializeMethodType(wantType, *genericArgumentsSubstitute);*/
  361. if (!mArguments[argIdx])
  362. goto NoMatch;
  363. if (!mExprEvaluator->CanCast(mArguments[argIdx], wantType))
  364. goto NoMatch;
  365. paramIdx++;
  366. argIdx++;
  367. if ((autoComplete != NULL) && (autoComplete->mIsCapturingMethodMatchInfo))
  368. {
  369. auto methodMatchInfo = autoComplete->mMethodMatchInfo;
  370. if (!methodMatchInfo->mHadExactMatch)
  371. {
  372. bool isBetter = false;
  373. bool isWorse = false;
  374. int methodIdx = (int)methodMatchInfo->mInstanceList.size() - 1;
  375. if (methodMatchInfo->mBestIdx < (int)methodMatchInfo->mInstanceList.size())
  376. {
  377. auto prevMethodMatchEntry = &methodMatchInfo->mInstanceList[methodMatchInfo->mBestIdx];
  378. if (checkMethod->mParams.Size() < (int)mArguments.size())
  379. {
  380. isWorse = true;
  381. }
  382. else if (prevMethodMatchEntry->mDwSubprogram->mParams.Size() < (int) mArguments.size())
  383. {
  384. isBetter = true;
  385. }
  386. else
  387. {
  388. //BfMethodInstance* prevMethodInstance = mModule->GetRawMethodInstanceAtIdx(prevMethodMatchEntry->mTypeInstance, prevMethodMatchEntry->mMethodDef->mIdx);
  389. DbgSubprogram* prevMethodInstance = prevMethodMatchEntry->mDwSubprogram;
  390. CompareMethods(prevMethodInstance, &prevMethodMatchEntry->mDwGenericArguments,
  391. methodInstance, genericArgumentsSubstitute, &isBetter, &isWorse, true);
  392. }
  393. }
  394. if ((argIdx > methodMatchInfo->mMostParamsMatched) ||
  395. ((argIdx == methodMatchInfo->mMostParamsMatched) && (isBetter)) ||
  396. ((argIdx == methodMatchInfo->mMostParamsMatched) && (methodIdx == methodMatchInfo->mPrevBestIdx) && (!isWorse)))
  397. {
  398. methodMatchInfo->mBestIdx = methodIdx;
  399. methodMatchInfo->mMostParamsMatched = argIdx;
  400. }
  401. }
  402. }
  403. }
  404. //TODO: Does this ever get hit?
  405. // Not enough arguments?
  406. if (argIdx < (int)mArguments.size())
  407. {
  408. goto NoMatch;
  409. }
  410. // Method is applicable, check to see which method is better
  411. if (mBestMethodDef != NULL)
  412. {
  413. bool isBetter = false;
  414. bool isWorse = false;
  415. //BfMethodInstance* prevMethodInstance = mModule->GetRawMethodInstanceAtIdx(mBestMethodTypeInstance, mBestMethodDef->mIdx);
  416. DbgSubprogram* prevMethodInstance = mBestMethodDef;
  417. CompareMethods(prevMethodInstance, &mBestMethodGenericArguments, methodInstance, genericArgumentsSubstitute, &isBetter, &isWorse, false);
  418. // If we had both a 'better' and 'worse', that's ambiguous because the methods are each better in different ways (not allowed)
  419. // And if neither better nor worse then they are equally good, which is not allowed either
  420. if (((!isBetter) && (!isWorse)) || ((isBetter) && (isWorse)))
  421. {
  422. // When we have [Checked] and [Unchecked] both, they will confict here but be equal
  423. if (!prevMethodInstance->Equals(methodInstance))
  424. {
  425. mExprEvaluator->Fail(StrFormat("Ambiguous method call between '%s' and '%s'", prevMethodInstance->ToString().c_str(),
  426. methodInstance->ToString().c_str()), mTargetSrc);
  427. }
  428. }
  429. if (!isBetter)
  430. goto Done;
  431. }
  432. if ((autoComplete != NULL) && (autoComplete->mIsCapturingMethodMatchInfo))
  433. {
  434. auto methodMatchInfo = autoComplete->mMethodMatchInfo;
  435. // Try to persist with previous partial match, if we have one - this keeps us from locking onto
  436. // an incorrect method just because it had the current number of params that we've typed so far
  437. if (methodMatchInfo->mPrevBestIdx == -1)
  438. {
  439. methodMatchInfo->mHadExactMatch = true;
  440. methodMatchInfo->mBestIdx = (int) methodMatchInfo->mInstanceList.size() - 1;
  441. }
  442. }
  443. hadMatch = true;
  444. mBestMethodDef = checkMethod;
  445. NoMatch:
  446. if (!hadMatch)
  447. {
  448. if (mBestMethodDef != NULL)
  449. return true;
  450. //TODO:
  451. /*if ((mHadExplicitGenericArguments) && (mBestMethodGenericArguments.size() != checkMethod->mGenericParams.size()))
  452. return true;*/
  453. // At least prefer a backup method that we have an address for
  454. if ((mBackupMethodDef != NULL) && (mBackupMethodDef->mBlock.mLowPC != 0))
  455. return true;
  456. mBackupMethodDef = checkMethod;
  457. // Lie temporarily to store at least one candidate (but mBestMethodDef is still NULL)
  458. hadMatch = true;
  459. }
  460. if (hadMatch)
  461. {
  462. mBestMethodTypeInstance = typeInstance;
  463. if (!mHadExplicitGenericArguments)
  464. {
  465. mBestMethodGenericArguments = mCheckMethodGenericArguments;
  466. }
  467. }
  468. Done:
  469. if ((autoComplete != NULL) && (autoComplete->mIsCapturingMethodMatchInfo) && (genericArgumentsSubstitute != NULL))
  470. {
  471. auto methodMatchInfo = autoComplete->mMethodMatchInfo;
  472. methodMatchInfo->mInstanceList[methodMatchInfo->mInstanceList.size() - 1].mDwGenericArguments = *genericArgumentsSubstitute;
  473. }
  474. return true;
  475. }
  476. bool DwMethodMatcher::CheckType(DbgType* typeInstance, bool isFailurePass)
  477. {
  478. typeInstance = typeInstance->RemoveModifiers();
  479. if (typeInstance->IsPointer())
  480. typeInstance = typeInstance->mTypeParam;
  481. typeInstance = typeInstance->GetPrimaryType();
  482. //bool allowPrivate = typeInstance == mExprEvaluator->GetCurrentType();
  483. //bool allowProtected = allowPrivate || mExprEvaluator->TypeIsSubTypeOf(mExprEvaluator->GetCurrentType(), typeInstance);
  484. bool allowPrivate = true;
  485. bool allowProtected = true;
  486. auto curType = typeInstance;
  487. bool wantCtor = false;
  488. auto baseItr = typeInstance->mBaseTypes.begin();
  489. auto altItr = typeInstance->mAlternates.begin();
  490. while (true)
  491. {
  492. bool foundMethodInType = false;
  493. curType->PopulateType();
  494. // Why did we have this "&&" check on there?
  495. // It made it so invocations would fail unless we had autocompleted the type
  496. if ((curType->mNeedsGlobalsPopulated)
  497. /*&& ((curType->IsNamespace()) || (curType->IsRoot()))*/)
  498. {
  499. // These aren't proper TPI types so we don't have any method declarations until we PopulateTypeGlobals
  500. mExprEvaluator->mDbgModule->PopulateTypeGlobals(curType);
  501. }
  502. for (auto methodNameEntry : curType->mMethodNameList)
  503. {
  504. if ((methodNameEntry->mCompileUnitId != -1) && (methodNameEntry->mName == mMethodName))
  505. {
  506. // If we hot-replaced this type then we replaced and parsed all the methods too
  507. if (!curType->mCompileUnit->mDbgModule->IsObjectFile())
  508. curType->mCompileUnit->mDbgModule->MapCompileUnitMethods(methodNameEntry->mCompileUnitId);
  509. methodNameEntry->mCompileUnitId = -1;
  510. }
  511. }
  512. auto checkMethod = curType->mMethodList.mHead;
  513. while (checkMethod != NULL)
  514. {
  515. /*if ((!checkMethod->mHasThis) && (!checkStatic))
  516. continue;
  517. if ((checkMethod->mHasThis) && (!checkNonStatic))
  518. continue;*/
  519. // These can only be invoked when the target itself is the interface
  520. /*if (checkMethod->mExplicitInterface != NULL)
  521. continue;*/
  522. if ((wantCtor) && (checkMethod->mMethodType != DbgMethodType_Ctor))
  523. {
  524. checkMethod = checkMethod->mNext;
  525. continue;
  526. }
  527. if (!wantCtor)
  528. {
  529. if (checkMethod->mMethodType != DbgMethodType_Normal)
  530. {
  531. checkMethod = checkMethod->mNext;
  532. continue;
  533. }
  534. if ((checkMethod->mName == NULL) || (checkMethod->mName != mMethodName))
  535. {
  536. checkMethod = checkMethod->mNext;
  537. continue;
  538. }
  539. }
  540. if ((!isFailurePass) && (!CheckProtection(checkMethod->mProtection, allowProtected, allowPrivate)))
  541. {
  542. checkMethod = checkMethod->mNext;
  543. continue;
  544. }
  545. if (!curType->mHasGlobalsPopulated)
  546. mExprEvaluator->mDbgModule->PopulateTypeGlobals(curType);
  547. /*if (!foundMethodInType)
  548. {
  549. if (curType->mCompileUnit->mLanguage != DbgLanguage_Beef)
  550. {
  551. String fullMethodName = String(curType->mTypeName) + "::" + mMethodName;
  552. curType->mCompileUnit->mDbgModule->EnsureMethodMapped(fullMethodName.c_str());
  553. }
  554. foundMethodInType = true;
  555. }*/
  556. if (!CheckMethod(curType, checkMethod))
  557. return false;
  558. checkMethod = checkMethod->mNext;
  559. }
  560. if (mBestMethodDef != NULL)
  561. {
  562. if ((mBestMethodDef->mVirtual) && (mBestMethodDef->mVTableLoc == -1))
  563. {
  564. // It's an override, keep searching through the base types to find the original method declaration
  565. mBestMethodDef = NULL;
  566. mBackupMethodDef = NULL;
  567. }
  568. else
  569. return true;
  570. }
  571. /*if (baseItr != typeInstance->mBaseTypes.end())
  572. {
  573. auto baseTypeEntry = *baseItr;
  574. curType = baseTypeEntry->mBaseType;
  575. baseItr++;
  576. continue;;
  577. }*/
  578. if (altItr != typeInstance->mAlternates.end())
  579. {
  580. curType = *altItr;
  581. ++altItr;
  582. continue;
  583. }
  584. /*allowPrivate = false;
  585. if ((isFailurePass) && (mBackupMethodDef != NULL))
  586. break;*/
  587. break;
  588. }
  589. if (mBestMethodDef == NULL)
  590. {
  591. // FAILED, but select the first method which will fire an actual error on param type matching
  592. mBestMethodDef = mBackupMethodDef;
  593. for (auto subType : typeInstance->mSubTypeList)
  594. {
  595. if ((subType->mName == NULL) || (subType->IsGlobalsContainer()))
  596. {
  597. if (!CheckType(subType, isFailurePass))
  598. return false;
  599. if (mBestMethodDef != NULL)
  600. break;
  601. }
  602. }
  603. if (mBestMethodDef == NULL)
  604. {
  605. for (auto baseTypeEntry : typeInstance->mBaseTypes)
  606. {
  607. if (!CheckType(baseTypeEntry->mBaseType, isFailurePass))
  608. return false;
  609. if (mBestMethodDef != NULL)
  610. break;
  611. }
  612. }
  613. }
  614. return true;
  615. }
  616. //////////////////////////////////////////////////////////////////////////
  617. DbgExprEvaluator::DbgExprEvaluator(WinDebugger* winDebugger, DbgModule* dbgModule, BfPassInstance* passInstance, int callStackIdx, int cursorPos)
  618. {
  619. mCountResultOverride = -1;
  620. mCapturingChildRef = true;
  621. mPassInstance = passInstance;
  622. mDebugger = winDebugger;
  623. mLanguage = DbgLanguage_NotSet;
  624. mOrigDbgModule = dbgModule;
  625. if (dbgModule != NULL)
  626. {
  627. mDebugTarget = dbgModule->mDebugTarget;
  628. mDbgModule = dbgModule->GetLinkedModule();
  629. }
  630. else
  631. {
  632. mDebugTarget = NULL;
  633. mDbgModule = NULL;
  634. }
  635. mDbgCompileUnit = NULL;
  636. mExplicitThisExpr = NULL;
  637. mExpectingType = NULL;
  638. mCurMethod = NULL;
  639. mIgnoreErrors = false;
  640. mCallStackIdx = callStackIdx;
  641. mCursorPos = cursorPos;
  642. mAutoComplete = NULL;
  643. mIsEmptyTarget = (dbgModule == NULL) || (dbgModule->mDebugTarget->mIsEmpty);
  644. mExpressionFlags = DwEvalExpressionFlag_None;
  645. mHadSideEffects = false;
  646. mBlockedSideEffects = false;
  647. mReferenceId = NULL;
  648. mIsComplexExpression = false;
  649. mHadMemberReference = false;
  650. mCreatedPendingCall = false;
  651. mStackSearch = NULL;
  652. mValidateOnly = false;
  653. mReceivingValue = NULL;
  654. mCallResults = NULL;
  655. mCallResultIdx = 0;
  656. mCallStackPreservePos = 0;
  657. mPropGet = NULL;
  658. mPropSet = NULL;
  659. mPropSrc = NULL;
  660. }
  661. DbgExprEvaluator::~DbgExprEvaluator()
  662. {
  663. delete mStackSearch;
  664. }
  665. DbgTypedValue DbgExprEvaluator::GetInt(int value)
  666. {
  667. DbgTypedValue dbgValue;
  668. dbgValue.mType = mDbgModule->GetPrimitiveType(DbgType_i32, GetLanguage());
  669. dbgValue.mInt32 = value;
  670. return dbgValue;
  671. }
  672. DbgTypedValue DbgExprEvaluator::GetString(const StringImpl& str)
  673. {
  674. String* resultPtr;
  675. mDebugger->mLiteralSet.TryAdd(str, &resultPtr);
  676. DbgTypedValue dbgValue;
  677. auto language = GetLanguage();
  678. auto charPtrType = mDbgModule->GetPrimitiveType((language == DbgLanguage_Beef) ? DbgType_UChar : DbgType_SChar, language);
  679. if (charPtrType != NULL)
  680. charPtrType = mDbgModule->GetPointerType(charPtrType);
  681. if (charPtrType != NULL)
  682. {
  683. dbgValue.mType = charPtrType;
  684. dbgValue.mLocalPtr = resultPtr->c_str();
  685. dbgValue.mIsLiteral = true;
  686. dbgValue.mDataLen = resultPtr->mLength;
  687. }
  688. return dbgValue;
  689. }
  690. void DbgExprEvaluator::Fail(const StringImpl& error, BfAstNode* node)
  691. {
  692. if ((!mIgnoreErrors) && (mPassInstance != NULL))
  693. mPassInstance->Fail(error, node);
  694. }
  695. void DbgExprEvaluator::Warn(const StringImpl& error, BfAstNode * node)
  696. {
  697. if ((!mIgnoreErrors) && (mPassInstance != NULL))
  698. mPassInstance->Warn(0, error, node);
  699. }
  700. DbgType* DbgExprEvaluator::GetExpectingType()
  701. {
  702. if ((mExpectingType == NULL) && (!mExpectingTypeName.empty()))
  703. {
  704. mExpectingType = ResolveTypeRef(mExpectingTypeName);
  705. mExpectingTypeName.clear();
  706. }
  707. return mExpectingType;
  708. }
  709. void DbgExprEvaluator::GetNamespaceSearch()
  710. {
  711. if (!mNamespaceSearch.empty())
  712. return;
  713. auto currentMethod = GetCurrentMethod();
  714. if (currentMethod != NULL)
  715. {
  716. auto parent = currentMethod->GetParent();
  717. while (parent != NULL)
  718. {
  719. parent = parent->GetPrimaryType();
  720. mNamespaceSearch.push_back(parent);
  721. parent = parent->mParent;
  722. }
  723. }
  724. if (!mNamespaceSearchStr.empty())
  725. {
  726. auto language = GetLanguage();
  727. int lastComma = -1;
  728. for (int i = 0; i < (int)mNamespaceSearchStr.length(); i++)
  729. {
  730. if (mNamespaceSearchStr[i] == ',')
  731. {
  732. String namespaceEntry = mNamespaceSearchStr.Substring(lastComma + 1, i - lastComma - 1);
  733. auto dbgTypeEntry = mDbgModule->mTypeMap.Find(namespaceEntry.c_str(), language);
  734. if (dbgTypeEntry != NULL)
  735. mNamespaceSearch.push_back(dbgTypeEntry->mValue);
  736. lastComma = i;
  737. }
  738. }
  739. String namespaceEntry = mNamespaceSearchStr.Substring(lastComma + 1);
  740. auto dbgTypeEntry = mDbgModule->mTypeMap.Find(namespaceEntry.c_str(), language);
  741. if (dbgTypeEntry != NULL)
  742. mNamespaceSearch.push_back(dbgTypeEntry->mValue);
  743. }
  744. }
  745. DbgType* DbgExprEvaluator::ResolveSubTypeRef(DbgType* checkType, const StringImpl& name)
  746. {
  747. checkType->PopulateType();
  748. for (auto subType : checkType->mSubTypeList)
  749. {
  750. if (strcmp(subType->mTypeName, name.c_str()) == 0)
  751. return subType;
  752. }
  753. for (auto checkBaseType : checkType->mBaseTypes)
  754. {
  755. DbgType* subType = ResolveSubTypeRef(checkBaseType->mBaseType, name);
  756. if (subType != NULL)
  757. return subType;
  758. }
  759. return NULL;
  760. }
  761. DbgType* DbgExprEvaluator::FixType(DbgType* dbgType)
  762. {
  763. if (dbgType->IsBfObject())
  764. dbgType = mDbgModule->GetPointerType(dbgType);
  765. return dbgType;
  766. }
  767. DbgTypedValue DbgExprEvaluator::FixThis(const DbgTypedValue& thisVal)
  768. {
  769. /*if ((thisVal.mType != NULL) && (thisVal.mType->GetLanguage() == DbgLanguage_Beef) &&
  770. (!thisVal.mType->IsBfObjectPtr()) && (thisVal.mType->IsPointer()))
  771. {
  772. // Beef structs expect 'this' as a valuetype, not a pointer
  773. DbgTypedValue fixedThisVal;
  774. fixedThisVal.mType = thisVal.mType->mTypeParam;
  775. fixedThisVal.mSrcAddress = thisVal.mPtr;
  776. fixedThisVal.mPtr = thisVal.mPtr;
  777. int byteCount = fixedThisVal.mType->GetByteCount();
  778. if (byteCount <= 8) // For typed primitive loads
  779. mDebugger->ReadMemory(fixedThisVal.mSrcAddress, byteCount, &fixedThisVal.mInt64);
  780. return fixedThisVal;
  781. }*/
  782. return thisVal;
  783. }
  784. DbgType* DbgExprEvaluator::ResolveTypeRef(BfTypeReference* typeRef)
  785. {
  786. mDbgModule->ParseTypeData();
  787. if (auto ptrTypeRef = BfNodeDynCastExact<BfPointerTypeRef>(typeRef))
  788. {
  789. // If it's a pointer type ref then create our own type
  790. auto innerType = ResolveTypeRef(ptrTypeRef->mElementType);
  791. if (innerType == NULL)
  792. return NULL;
  793. return mDbgModule->GetPointerType(innerType);
  794. }
  795. if (auto arrayTypeRef = BfNodeDynCastExact<BfArrayTypeRef>(typeRef))
  796. {
  797. if (arrayTypeRef->mParams.size() == 1)
  798. {
  799. if (auto literalExpr = BfNodeDynCastExact<BfLiteralExpression>(arrayTypeRef->mParams[0]))
  800. {
  801. auto elementType = ResolveTypeRef(arrayTypeRef->mElementType);
  802. if (elementType == NULL)
  803. return NULL;
  804. int count = 1;
  805. if ((literalExpr->mValue.mTypeCode >= BfTypeCode_Int16) && (literalExpr->mValue.mTypeCode <= BfTypeCode_UIntUnknown))
  806. {
  807. count = literalExpr->mValue.mInt32;
  808. if (count < 0)
  809. {
  810. Fail(StrFormat("Illegal array size"), arrayTypeRef->mParams[0]);
  811. count = 1;
  812. }
  813. }
  814. else
  815. {
  816. Fail(StrFormat("Illegal array size type"), arrayTypeRef->mParams[0]);
  817. }
  818. return mDbgModule->GetSizedArrayType(elementType, count);
  819. }
  820. }
  821. }
  822. if (auto declTypeRef = BfNodeDynCastExact<BfExprModTypeRef>(typeRef))
  823. {
  824. mResult = DbgTypedValue();
  825. VisitChild(declTypeRef->mTarget);
  826. auto type = mResult.mType;
  827. mResult = DbgTypedValue();
  828. return type;
  829. }
  830. String name = typeRef->ToString();
  831. if (name.StartsWith("_T_"))
  832. {
  833. auto dbgModule = mDbgModule;
  834. char* endPtr = NULL;
  835. int typeIdx = strtol(name.c_str() + 3, &endPtr, 10);
  836. if ((endPtr != NULL) && (*endPtr == '_'))
  837. {
  838. int moduleIdx = typeIdx;
  839. typeIdx = atoi(endPtr + 1);
  840. mDebugTarget->mDbgModuleMap.TryGetValue(moduleIdx, &dbgModule);
  841. }
  842. if ((dbgModule != NULL) && (typeIdx >= 0) && (typeIdx < (int)dbgModule->mTypes.size()))
  843. return dbgModule->mTypes[typeIdx];
  844. }
  845. auto entry = mDbgModule->mTypeMap.Find(name.c_str(), GetLanguage());
  846. if (entry != NULL)
  847. return FixType(entry->mValue);
  848. if (mExplicitThis)
  849. {
  850. bool isPtr = typeRef->IsA<BfPointerTypeRef>();
  851. if (isPtr)
  852. {
  853. BfPointerTypeRef* ptrTypeRef = (BfPointerTypeRef*)typeRef;
  854. BfTypeReference* innerTypeRef = ptrTypeRef->mElementType;
  855. name = innerTypeRef->ToString();
  856. }
  857. auto checkType = mExplicitThis.mType;
  858. if (checkType->IsPointer())
  859. checkType = checkType->mTypeParam;
  860. ResolveSubTypeRef(checkType, name);
  861. }
  862. auto currentType = GetCurrentType();
  863. if (currentType != NULL)
  864. {
  865. GetNamespaceSearch();
  866. for (auto usingNamespace : mNamespaceSearch)
  867. {
  868. auto usingNamespaceString = usingNamespace->ToString();
  869. entry = mDbgModule->mTypeMap.Find((usingNamespaceString + "." + name).c_str(), GetLanguage());
  870. if (entry != NULL)
  871. return FixType(entry->mValue);
  872. }
  873. }
  874. Fail(StrFormat("Unable to locate type"), typeRef);
  875. return NULL;
  876. }
  877. DbgType* DbgExprEvaluator::ResolveTypeRef(BfAstNode* typeRef, BfAstNode** parentChildRef)
  878. {
  879. StringT<128> name = typeRef->ToString();
  880. if ((name.StartsWith("_T_")) && ((int)name.IndexOf('.') == -1))
  881. {
  882. int endIdx = name.length();
  883. for (int i = 3; i < (int)name.length(); i++)
  884. {
  885. char c = name[i];
  886. if (((c < '0') || (c > '9')) && (c != '_'))
  887. {
  888. endIdx = i;
  889. break;
  890. }
  891. }
  892. auto dbgModule = mDbgModule;
  893. char* endPtr = NULL;
  894. int typeIdx = strtol(name.c_str() + 3, &endPtr, 10);
  895. if ((endPtr != NULL) && (*endPtr == '_'))
  896. {
  897. int moduleIdx = typeIdx;
  898. typeIdx = atoi(endPtr + 1);
  899. mDebugTarget->mDbgModuleMap.TryGetValue(moduleIdx, &dbgModule);
  900. }
  901. if ((dbgModule != NULL) && (typeIdx >= 0) && (typeIdx < (int)dbgModule->mTypes.size()))
  902. {
  903. if ((mExplicitThisExpr != NULL) && (parentChildRef != NULL))
  904. mDeferredInsertExplicitThisVector.push_back(NodeReplaceRecord(typeRef, parentChildRef, true));
  905. DbgType* dbgType = dbgModule->mTypes[typeIdx];
  906. for (int i = endIdx; i < (int)name.length(); i++)
  907. {
  908. if (name[i] == '*')
  909. dbgType = dbgModule->GetPointerType(dbgType);
  910. }
  911. return dbgType;
  912. }
  913. }
  914. /*for (int i = 1; i < (int)name.length(); i++)
  915. {
  916. if ((name[i] == ':') && (name[i - 1] == ':'))
  917. {
  918. name[i] = '.';
  919. name.erase(name.begin() + i - 1);
  920. i--;
  921. }
  922. }*/
  923. auto language = GetLanguage();
  924. auto entry = mDbgModule->FindType(name.c_str(), language);
  925. if (entry != NULL)
  926. return entry->mValue;
  927. auto currentType = GetCurrentType();
  928. if (currentType != NULL)
  929. {
  930. GetNamespaceSearch();
  931. for (auto usingNamespace : mNamespaceSearch)
  932. {
  933. auto usingNamespaceString = usingNamespace->ToString();
  934. entry = mDbgModule->FindType((usingNamespaceString + "." + name).c_str(), language);
  935. if (entry != NULL)
  936. return entry->mValue;
  937. }
  938. }
  939. Fail("Unable to locate type", typeRef);
  940. return NULL;
  941. }
  942. DbgType* DbgExprEvaluator::ResolveTypeRef(const StringImpl& typeName)
  943. {
  944. auto entry = mDbgModule->mTypeMap.Find(typeName.c_str(), GetLanguage());
  945. if (entry != NULL)
  946. return entry->mValue;
  947. mPassInstance->Fail("Unable to locate type: " + typeName);
  948. return NULL;
  949. }
  950. bool DbgExprEvaluator::TypeIsSubTypeOf(DbgType* srcType, DbgType* wantType, int* thisOffset, addr_target* thisAddr)
  951. {
  952. if (srcType == NULL)
  953. return false;
  954. srcType = srcType->GetPrimaryType();
  955. wantType = wantType->GetPrimaryType();
  956. if ((wantType->IsPrimitiveType()) && (srcType->IsPrimitiveType()))
  957. {
  958. return wantType->mTypeCode == srcType->mTypeCode;
  959. }
  960. if ((srcType == NULL) || (wantType == NULL))
  961. return false;
  962. if (srcType->Equals(wantType))
  963. return true;
  964. if (srcType->mTypeCode == DbgType_TypeDef)
  965. return TypeIsSubTypeOf(srcType->mTypeParam, wantType);
  966. if (wantType->mTypeCode == DbgType_TypeDef)
  967. return TypeIsSubTypeOf(srcType, wantType->mTypeParam);
  968. srcType->PopulateType();
  969. for (auto srcBaseType : srcType->mBaseTypes)
  970. {
  971. bool isSubtype = TypeIsSubTypeOf(srcBaseType->mBaseType, wantType);
  972. if (isSubtype)
  973. {
  974. if (srcBaseType->mVTableOffset != -1)
  975. {
  976. if (thisAddr == NULL)
  977. return false;
  978. int32 virtThisOffset = 0;
  979. addr_target vtableAddr = 0;
  980. gDebugger->ReadMemory(*thisAddr, sizeof(addr_target), &vtableAddr);
  981. gDebugger->ReadMemory(vtableAddr + srcBaseType->mVTableOffset * sizeof(int32), sizeof(int32), &virtThisOffset);
  982. *thisOffset += virtThisOffset;
  983. }
  984. else if (thisOffset != NULL)
  985. *thisOffset += srcBaseType->mThisOffset;
  986. return true;
  987. }
  988. }
  989. return false;
  990. }
  991. DbgTypedValue DbgExprEvaluator::GetBeefTypeById(int typeId)
  992. {
  993. if (mDebugTarget->mTargetBinary == NULL)
  994. return DbgTypedValue();
  995. if (mDebugTarget->mTargetBinary->mBfTypesInfoAddr == 0)
  996. {
  997. mDebugTarget->mTargetBinary->mBfTypesInfoAddr = -1;
  998. mDebugTarget->mTargetBinary->ParseTypeData();
  999. auto typeTypeEntry = mDebugTarget->mTargetBinary->FindType("System.Type", DbgLanguage_Beef);
  1000. if ((typeTypeEntry != NULL) && (typeTypeEntry->mValue != NULL))
  1001. {
  1002. auto typeType = typeTypeEntry->mValue;
  1003. mDebugTarget->mTargetBinary->mBfTypeType = typeType;
  1004. if (typeType->mNeedsGlobalsPopulated)
  1005. typeType->mCompileUnit->mDbgModule->PopulateTypeGlobals(typeType);
  1006. for (auto member : typeType->mMemberList)
  1007. {
  1008. if ((member->mIsStatic) && (member->mName != NULL) && (strcmp(member->mName, "sTypes") == 0) && (member->mLocationData != NULL))
  1009. {
  1010. auto stackFrame = GetStackFrame();
  1011. DbgAddrType addrType;
  1012. mDebugTarget->mTargetBinary->mBfTypesInfoAddr = member->mCompileUnit->mDbgModule->EvaluateLocation(NULL, member->mLocationData, member->mLocationLen, stackFrame, &addrType);
  1013. }
  1014. }
  1015. if (mDebugTarget->mTargetBinary->mBfTypesInfoAddr <= 0)
  1016. {
  1017. mDebugTarget->mTargetBinary->ParseSymbolData();
  1018. auto entry = mDebugTarget->mTargetBinary->mSymbolNameMap.Find(
  1019. #ifdef BF_DBG_64
  1020. "?sTypes@Type@System@bf@@2PEAPEAV123@A"
  1021. #else
  1022. "?sTypes@Type@System@bf@@2PAPAV123@A"
  1023. #endif
  1024. );
  1025. if (entry)
  1026. mDebugTarget->mTargetBinary->mBfTypesInfoAddr = entry->mValue->mAddress;
  1027. }
  1028. }
  1029. }
  1030. if (mDebugTarget->mTargetBinary->mBfTypesInfoAddr > 0)
  1031. {
  1032. DbgTypedValue typedVal;
  1033. typedVal.mType = mDebugTarget->mTargetBinary->mBfTypeType;
  1034. addr_target addr = mDebugTarget->mTargetBinary->mBfTypesInfoAddr + typeId * sizeof(addr_target);
  1035. typedVal.mSrcAddress = mDebugger->ReadMemory<addr_target>(addr);
  1036. return typedVal;
  1037. }
  1038. return DbgTypedValue();
  1039. }
  1040. void DbgExprEvaluator::BeefStringToString(addr_target addr, String& outStr)
  1041. {
  1042. mDebugTarget->GetCompilerSettings();
  1043. int objectSize = mDebugTarget->mBfObjectSize;
  1044. int32 strLen = 0;
  1045. addr_target charPtr = 0;
  1046. if (!mDebugTarget->mBfHasLargeStrings)
  1047. {
  1048. strLen = mDebugger->ReadMemory<int32>(addr + objectSize);
  1049. int32 allocSizeAndFlags = mDebugger->ReadMemory<int32>(addr + objectSize + 4);
  1050. if ((allocSizeAndFlags & 0x40000000) != 0)
  1051. charPtr = mDebugger->ReadMemory<addr_target>(addr + objectSize + 4 + 4);
  1052. else
  1053. charPtr = addr + objectSize + 4 + 4;
  1054. }
  1055. else
  1056. {
  1057. strLen = mDebugger->ReadMemory<int32>(addr + objectSize);
  1058. int64 allocSizeAndFlags = mDebugger->ReadMemory<int64>(addr + objectSize + 8);
  1059. if ((allocSizeAndFlags & 0x40000000'00000000LL) != 0)
  1060. charPtr = mDebugger->ReadMemory<addr_target>(addr + objectSize + 8 + 8);
  1061. else
  1062. charPtr = addr + objectSize + 4 + 4;
  1063. }
  1064. if ((strLen > 0) && (strLen < 4096))
  1065. {
  1066. outStr.Append('?', strLen);
  1067. mDebugger->ReadMemory(charPtr, strLen, &outStr[outStr.length() - strLen]);
  1068. }
  1069. }
  1070. void DbgExprEvaluator::BeefStringToString(const DbgTypedValue& val, String& outStr)
  1071. {
  1072. mDebugTarget->GetCompilerSettings();
  1073. auto useVal = val;
  1074. if (useVal.mType->IsBfObjectPtr())
  1075. {
  1076. useVal.mType = useVal.mType->mTypeParam;
  1077. useVal.mSrcAddress = useVal.mPtr;
  1078. }
  1079. BeefStringToString(useVal.mSrcAddress, outStr);
  1080. }
  1081. void DbgExprEvaluator::BeefTypeToString(const DbgTypedValue& val, String& outStr)
  1082. {
  1083. if (!val)
  1084. return;
  1085. mDebugTarget->GetCompilerSettings();
  1086. auto useVal = val;
  1087. if (useVal.mType->IsBfObjectPtr())
  1088. {
  1089. useVal.mType = useVal.mType->mTypeParam;
  1090. useVal.mSrcAddress = useVal.mPtr;
  1091. }
  1092. typedef int32 _TypeId;
  1093. typedef uint32 _TypeFlags;
  1094. typedef int8 _TypeCode;
  1095. #pragma pack(push, 1)
  1096. struct _Type
  1097. {
  1098. int32 mSize;
  1099. _TypeId mTypeId;
  1100. _TypeId mBoxedType;
  1101. _TypeFlags mTypeFlags;
  1102. int32 mMemberDataOffset;
  1103. _TypeCode mTypeCode;
  1104. uint8 mAlign;
  1105. };
  1106. struct _PointerType : _Type
  1107. {
  1108. int16 mPadding0;
  1109. _TypeCode mElementType;
  1110. };
  1111. struct _SizedArrayType : _Type
  1112. {
  1113. int16 mPadding0;
  1114. _TypeId mElementType;
  1115. int32 mElementCount;
  1116. };
  1117. struct _String
  1118. {
  1119. };
  1120. struct _MethodData
  1121. {
  1122. };
  1123. struct _FieldData
  1124. {
  1125. };
  1126. struct _ClassVData
  1127. {
  1128. };
  1129. struct _TypeInstance : public _Type
  1130. {
  1131. #ifdef BF_DBG_32
  1132. int16 mPadding0;
  1133. #else
  1134. int16 mPadding0;
  1135. #endif
  1136. addr_target mTypeClassVData;
  1137. addr_target mName;
  1138. addr_target mNamespace;
  1139. int32 mInstSize;
  1140. int32 mInstAlign;
  1141. int32 mCustomAttributesIdx;
  1142. _TypeId mBaseType;
  1143. _TypeId mUnderlyingType;
  1144. _TypeId mOuterType;
  1145. int32 mInheritanceId;
  1146. int32 mInheritanceCount;
  1147. uint8 mInterfaceSlot;
  1148. uint8 mInterfaceCount;
  1149. int16 mInterfaceMethodCount;
  1150. int16 mMethodDataCount;
  1151. int16 mPropertyDataCount;
  1152. int16 mFieldDataCount;
  1153. #ifdef BF_DBG_32
  1154. int16 mPadding1;
  1155. #else
  1156. int8 mPadding1[6];
  1157. #endif
  1158. addr_target mInterfaceDataPtr;
  1159. addr_target mInterfaceMethodTable;
  1160. addr_target mMethodDataPtr;
  1161. addr_target mPropertyDataPtr;
  1162. addr_target mFieldDataPtr;
  1163. addr_target mCustomAttrDataPtr;
  1164. };
  1165. struct _SpecializedGenericType : _TypeInstance
  1166. {
  1167. _TypeId mUnspecializedType;
  1168. #ifdef BF_DBG_64
  1169. int32 mPadding0;
  1170. #endif
  1171. addr_target mResolvedTypeRefs;
  1172. };
  1173. struct _ArrayType : _SpecializedGenericType
  1174. {
  1175. int32 mElementSize;
  1176. uint8 mRank;
  1177. uint8 mElemensDataOffset;
  1178. };
  1179. #pragma pack(pop)
  1180. int typeIdSize = sizeof(_TypeId);
  1181. int ptrSize = (int)sizeof(addr_target);
  1182. int objectSize = mDebugTarget->mBfObjectSize;
  1183. int typeSize = sizeof(_Type);
  1184. int typeInstanceSize = objectSize + sizeof(_TypeInstance);
  1185. auto addr = useVal.mSrcAddress;
  1186. auto typeAddr = addr + objectSize;
  1187. _TypeFlags typeFlags = mDebugger->ReadMemory<_TypeFlags>(typeAddr + offsetof(_Type, mTypeFlags));
  1188. if ((typeFlags & BfTypeFlags_Array) != 0)
  1189. {
  1190. _TypeId unspecializedTypeId = mDebugger->ReadMemory<_TypeId>(typeAddr + offsetof(_SpecializedGenericType, mUnspecializedType));
  1191. addr_target elementsArrayAddr = mDebugger->ReadMemory<addr_target>(typeAddr + offsetof(_SpecializedGenericType, mResolvedTypeRefs));
  1192. _TypeId elementTypeId = mDebugger->ReadMemory<_TypeId>(elementsArrayAddr);
  1193. auto elementType = GetBeefTypeById(elementTypeId);
  1194. BeefTypeToString(elementType, outStr);
  1195. outStr += "[";
  1196. int rank = mDebugger->ReadMemory<uint8>(typeAddr + offsetof(_ArrayType, mRank));
  1197. for (int commaIdx = 0; commaIdx < rank - 1; commaIdx++)
  1198. outStr += ",";
  1199. outStr += "]";
  1200. }
  1201. else if ((typeFlags & BfTypeFlags_Pointer) != 0)
  1202. {
  1203. _TypeId elementTypeId = mDebugger->ReadMemory<_TypeId>(typeAddr + offsetof(_PointerType, mElementType));
  1204. auto elementType = GetBeefTypeById(elementTypeId);
  1205. BeefTypeToString(elementType, outStr);
  1206. outStr += "*";
  1207. }
  1208. else if ((typeFlags & BfTypeFlags_Delegate) != 0)
  1209. {
  1210. outStr += "delegate";
  1211. }
  1212. else if ((typeFlags & BfTypeFlags_Function) != 0)
  1213. {
  1214. outStr += "function";
  1215. }
  1216. // else if ((typeFlags & BfTypeFlags_Tuple) != 0)
  1217. // {
  1218. // outStr += "function";
  1219. // }
  1220. else if ((typeFlags & BfTypeFlags_SizedArray) != 0)
  1221. {
  1222. _TypeId elementTypeId = mDebugger->ReadMemory<_TypeId>(typeAddr + objectSize + offsetof(_SizedArrayType, mElementType));
  1223. auto elementType = GetBeefTypeById(elementTypeId);
  1224. BeefTypeToString(elementType, outStr);
  1225. int elementCount = mDebugger->ReadMemory<int32>(typeAddr + objectSize + offsetof(_SizedArrayType, mElementCount));
  1226. outStr += StrFormat("[%d]", elementCount);
  1227. }
  1228. else if (((typeFlags & BfTypeFlags_Struct) != 0) || ((typeFlags & BfTypeFlags_TypedPrimitive) != 0) || ((typeFlags & BfTypeFlags_Object) != 0))
  1229. {
  1230. addr_target addr0 = typeAddr;
  1231. addr_target addr1 = typeAddr + offsetof(_Type, mTypeFlags);
  1232. addr_target addr2 = typeAddr + offsetof(_Type, mAlign);
  1233. addr_target addr3 = typeAddr + offsetof(_TypeInstance, mPadding0);
  1234. addr_target addr4 = typeAddr + offsetof(_TypeInstance, mTypeClassVData);
  1235. addr_target namePtr = mDebugger->ReadMemory<addr_target>(typeAddr + offsetof(_TypeInstance, mName));
  1236. addr_target namespacePtr = mDebugger->ReadMemory<addr_target>(typeAddr + offsetof(_TypeInstance, mNamespace));
  1237. int outerTypeId = mDebugger->ReadMemory<_TypeId>(typeAddr + offsetof(_TypeInstance, mOuterType));
  1238. DbgTypedValue outerType;
  1239. if (outerTypeId != 0)
  1240. {
  1241. outerType = GetBeefTypeById(outerTypeId);
  1242. BeefTypeToString(outerType, outStr);
  1243. outStr += ".";
  1244. }
  1245. else if (namespacePtr != 0)
  1246. {
  1247. String namespaceName;
  1248. BeefStringToString(namespacePtr, namespaceName);
  1249. if (!namespaceName.empty())
  1250. {
  1251. outStr += namespaceName;
  1252. outStr += ".";
  1253. }
  1254. }
  1255. BeefStringToString(namePtr, outStr);
  1256. if ((typeFlags & BfTypeFlags_SpecializedGeneric) != 0)
  1257. {
  1258. int unspecializedTypeId = mDebugger->ReadMemory<_TypeId>(addr + typeInstanceSize);
  1259. auto unspecializedType = GetBeefTypeById(unspecializedTypeId);
  1260. outStr += "<";
  1261. if (unspecializedType)
  1262. {
  1263. int startGenericIdx = 0;
  1264. int genericCount = mDebugger->ReadMemory<uint8>(unspecializedType.mSrcAddress + typeInstanceSize);
  1265. if (outerType)
  1266. {
  1267. int outerUnspecializedTypeId = mDebugger->ReadMemory<_TypeId>(outerType.mSrcAddress + typeInstanceSize);
  1268. auto outerUnspecializedType = GetBeefTypeById(outerUnspecializedTypeId);
  1269. startGenericIdx = mDebugger->ReadMemory<uint8>(outerUnspecializedType.mSrcAddress + typeInstanceSize);
  1270. }
  1271. addr_target genericParamsPtr = mDebugger->ReadMemory<addr_target>(addr + BF_ALIGN(typeInstanceSize + typeIdSize, ptrSize));
  1272. for (int i = startGenericIdx; i < genericCount; i++)
  1273. {
  1274. int genericParamTypeId = mDebugger->ReadMemory<_TypeId>(genericParamsPtr + i * typeIdSize);
  1275. if (i > startGenericIdx)
  1276. outStr += ", ";
  1277. BeefTypeToString(GetBeefTypeById(genericParamTypeId), outStr);
  1278. }
  1279. }
  1280. outStr += ">";
  1281. }
  1282. }
  1283. else
  1284. {
  1285. BfTypeCode typeCode = (BfTypeCode)mDebugger->ReadMemory<uint8>(typeAddr + (int)offsetof(_Type, mTypeCode));
  1286. if (typeCode == BfTypeCode_Pointer)
  1287. {
  1288. _TypeId elementType = mDebugger->ReadMemory<_TypeId>(typeAddr + offsetof(_PointerType, mElementType));
  1289. BeefTypeToString(GetBeefTypeById(elementType), outStr);
  1290. outStr += "*";
  1291. return;
  1292. }
  1293. switch (typeCode)
  1294. {
  1295. case BfTypeCode_None: outStr += "void"; break;
  1296. case BfTypeCode_CharPtr: outStr += "char8*"; break;
  1297. case BfTypeCode_Pointer: outStr += "*"; break;
  1298. case BfTypeCode_NullPtr: outStr += ""; break;
  1299. case BfTypeCode_Var: outStr += "var"; break;
  1300. case BfTypeCode_Let: outStr += "let"; break;
  1301. case BfTypeCode_Boolean: outStr += "bool"; break;
  1302. case BfTypeCode_Int8: outStr += "int8"; break;
  1303. case BfTypeCode_UInt8: outStr += "uint8"; break;
  1304. case BfTypeCode_Int16: outStr += "int16"; break;
  1305. case BfTypeCode_UInt16: outStr += "uint16"; break;
  1306. case BfTypeCode_Int32: outStr += "int32"; break;
  1307. case BfTypeCode_UInt32: outStr += "uint32"; break;
  1308. case BfTypeCode_Int64: outStr += "int64"; break;
  1309. case BfTypeCode_UInt64: outStr += "uint64"; break;
  1310. case BfTypeCode_IntPtr: outStr += "int"; break;
  1311. case BfTypeCode_UIntPtr: outStr += "uint"; break;
  1312. case BfTypeCode_IntUnknown: outStr += "int unknown"; break;
  1313. case BfTypeCode_UIntUnknown: outStr += "uint unknown"; break;
  1314. case BfTypeCode_Char8: outStr += "char8"; break;
  1315. case BfTypeCode_Char16: outStr += "char16"; break;
  1316. case BfTypeCode_Char32: outStr += "char32"; break;
  1317. case BfTypeCode_Float: outStr += "float"; break;
  1318. case BfTypeCode_Double: outStr += "double"; break;
  1319. }
  1320. }
  1321. }
  1322. CPUStackFrame* DbgExprEvaluator::GetStackFrame()
  1323. {
  1324. if (mIsEmptyTarget)
  1325. return NULL;
  1326. static CPUStackFrame emptyStackFrame;
  1327. if (mCallStackIdx == -1)
  1328. return &emptyStackFrame;
  1329. if (mDebugger->mRunState == RunState_NotStarted)
  1330. return &emptyStackFrame;
  1331. if (mDebugger->mCallStack.size() == 0)
  1332. mDebugger->UpdateCallStack();
  1333. if (mCallStackIdx >= (int)mDebugger->mCallStack.size())
  1334. return &emptyStackFrame;
  1335. return mDebugger->mCallStack[mCallStackIdx];
  1336. }
  1337. CPURegisters* DbgExprEvaluator::GetRegisters()
  1338. {
  1339. if (mIsEmptyTarget)
  1340. return NULL;
  1341. auto stackFrame = GetStackFrame();
  1342. if (stackFrame != NULL)
  1343. return &stackFrame->mRegisters;
  1344. return NULL;
  1345. }
  1346. DbgTypedValue DbgExprEvaluator::GetRegister(const StringImpl& regName)
  1347. {
  1348. if (mIsEmptyTarget)
  1349. return DbgTypedValue();
  1350. if (!mDebugger->mIsRunning)
  1351. return DbgTypedValue();
  1352. Array<RegForm>* regForms = NULL;
  1353. if (mCallStackIdx != -1)
  1354. {
  1355. if (mCallStackIdx < (int)mDebugger->mCallStack.size())
  1356. regForms = &mDebugger->mCallStack[mCallStackIdx]->mRegForms;
  1357. }
  1358. DbgTypedValue result = mDebugger->GetRegister(regName, GetLanguage(), GetRegisters(), regForms);
  1359. if ((result) && (mReferenceId != NULL))
  1360. {
  1361. int regNum = CPURegisters::GetCompositeRegister(result.mRegNum);
  1362. const char* regName = CPURegisters::GetRegisterName(regNum);
  1363. if (regName != NULL)
  1364. *mReferenceId = String("$") + regName;
  1365. }
  1366. return result;
  1367. }
  1368. DbgSubprogram* DbgExprEvaluator::GetCurrentMethod()
  1369. {
  1370. if (mIsEmptyTarget)
  1371. return NULL;
  1372. if (!mDebugger->mIsRunning)
  1373. return NULL;
  1374. if (mCallStackIdx == -1)
  1375. return NULL;
  1376. mDebugger->UpdateCallStackMethod(mCallStackIdx);
  1377. if (mCallStackIdx >= (int)mDebugger->mCallStack.size())
  1378. return NULL;
  1379. auto callStack = mDebugger->mCallStack[mCallStackIdx];
  1380. auto subProgram = callStack->mSubProgram;
  1381. if (subProgram != NULL)
  1382. subProgram->PopulateSubprogram();
  1383. return subProgram;
  1384. }
  1385. DbgType* DbgExprEvaluator::GetCurrentType()
  1386. {
  1387. auto curMethod = GetCurrentMethod();
  1388. if (curMethod != NULL)
  1389. return curMethod->mParentType;
  1390. return NULL;
  1391. }
  1392. DbgTypedValue DbgExprEvaluator::GetThis()
  1393. {
  1394. if (mExplicitThis)
  1395. return mExplicitThis;
  1396. String findName = "this";
  1397. CPUStackFrame* stackFrame = GetStackFrame();
  1398. if (stackFrame != NULL)
  1399. {
  1400. intptr valAddr;
  1401. DbgType* valType;
  1402. DbgAddrType addrType = DbgAddrType_Value;
  1403. if (mDebugTarget->GetValueByName(GetCurrentMethod(), findName, stackFrame, &valAddr, &valType, &addrType))
  1404. {
  1405. //valType = valType->RemoveModifiers();
  1406. return FixThis(ReadTypedValue(NULL, valType, valAddr, addrType));
  1407. }
  1408. if (mDebugTarget->GetValueByName(GetCurrentMethod(), "__closure", stackFrame, &valAddr, &valType, &addrType))
  1409. {
  1410. DbgTypedValue result = ReadTypedValue(NULL, valType, valAddr, addrType);
  1411. if (!result)
  1412. return result;
  1413. SetAndRestoreValue<bool> prevIgnoreError(mIgnoreErrors, true);
  1414. return FixThis(LookupField(NULL, result, "__this"));
  1415. }
  1416. }
  1417. return DbgTypedValue();
  1418. }
  1419. DbgTypedValue DbgExprEvaluator::GetDefaultTypedValue(DbgType* srcType)
  1420. {
  1421. DbgTypedValue typedValue;
  1422. typedValue.mType = srcType;
  1423. return typedValue;
  1424. }
  1425. String DbgExprEvaluator::TypeToString(DbgType* type)
  1426. {
  1427. return type->ToString();
  1428. }
  1429. bool DbgExprEvaluator::CheckHasValue(DbgTypedValue typedValue, BfAstNode* refNode)
  1430. {
  1431. if ((!typedValue) && (typedValue.mType != NULL))
  1432. {
  1433. mResult = DbgTypedValue();
  1434. Fail("Value required", refNode);
  1435. return false;
  1436. }
  1437. return true;
  1438. }
  1439. //TODO: Expand this
  1440. bool DbgExprEvaluator::CanCast(DbgTypedValue typedVal, DbgType* toType, BfCastFlags castFlags)
  1441. {
  1442. DbgType* fromType = typedVal.mType;
  1443. if (fromType == toType)
  1444. return true;
  1445. if ((fromType->IsConst()) && (!toType->IsConst()))
  1446. return false;
  1447. fromType = fromType->RemoveModifiers();
  1448. toType = toType->RemoveModifiers();
  1449. // Ptr -> const Ptr
  1450. if ((fromType->IsPointer()) && (toType->IsPointer()))
  1451. {
  1452. if (toType->mTypeParam->IsConst())
  1453. {
  1454. auto primaryFrom = fromType->mTypeParam->GetPrimaryType();
  1455. auto primaryTo = toType->mTypeParam->mTypeParam->GetPrimaryType();
  1456. if ((primaryFrom->IsCompositeType()) || (primaryTo->IsCompositeType()))
  1457. {
  1458. if (primaryFrom == primaryTo)
  1459. return true;
  1460. }
  1461. else if (primaryFrom->IsPrimitiveType())
  1462. {
  1463. return primaryFrom->mTypeCode == primaryTo->mTypeCode;
  1464. }
  1465. }
  1466. }
  1467. if ((fromType->IsCompositeType()) && ((toType->IsCompositeType() || (toType->IsInterface()))))
  1468. {
  1469. bool allowCast = false;
  1470. //TODO: Allow explicit interface casts on any object
  1471. //TODO: Insert cast checking code
  1472. int thisOffset = 0;
  1473. addr_target thisVal = typedVal.mSrcAddress;
  1474. if (TypeIsSubTypeOf(fromType, toType, &thisOffset, &thisVal))
  1475. {
  1476. return true;
  1477. }
  1478. }
  1479. if ((fromType->IsPrimitiveType()) && (toType->IsPrimitiveType()))
  1480. {
  1481. DbgTypeCode fromTypeCode = fromType->mTypeCode;
  1482. DbgTypeCode toTypeCode = toType->mTypeCode;
  1483. if ((fromTypeCode == toTypeCode))
  1484. return true;
  1485. // Must be from a default int to do an implicit constant cast, not casted by user, ie: (ushort)123
  1486. if ((toType->IsInteger()) /*&& (typedVal.mValue != NULL) && (fromTypeCode == DbgType_i32)*/)
  1487. {
  1488. // Allow constant ints to be implicitly downcasted if they fit
  1489. if (typedVal.mIsLiteral)
  1490. {
  1491. int64 srcVal = typedVal.GetInt64();
  1492. if (toType->IsSigned())
  1493. {
  1494. int64 minVal = -(1LL << (8 * toType->mSize - 1));
  1495. int64 maxVal = (1LL << (8 * toType->mSize - 1)) - 1;
  1496. if ((srcVal >= minVal) && (srcVal <= maxVal))
  1497. return true;
  1498. }
  1499. else if (toType->mSize == 8) // ulong
  1500. {
  1501. if (srcVal > 0)
  1502. return true;
  1503. }
  1504. else
  1505. {
  1506. int64 minVal = 0;
  1507. int64 maxVal = (1LL << (8 * toType->mSize)) - 1;
  1508. if ((srcVal >= minVal) && (srcVal <= maxVal))
  1509. return true;
  1510. }
  1511. }
  1512. }
  1513. switch (toTypeCode)
  1514. {
  1515. case DbgType_u8:
  1516. case DbgType_UChar:
  1517. switch (fromTypeCode)
  1518. {
  1519. case DbgType_UChar:
  1520. case DbgType_u8:
  1521. return true;
  1522. }
  1523. break;
  1524. case DbgType_SChar16:
  1525. case DbgType_i16:
  1526. switch (fromTypeCode)
  1527. {
  1528. case DbgType_i8:
  1529. case DbgType_i16:
  1530. case DbgType_SChar:
  1531. case DbgType_SChar16:
  1532. return true;
  1533. case DbgType_u8:
  1534. case DbgType_UChar:
  1535. return true;
  1536. }
  1537. break;
  1538. case DbgType_u16:
  1539. switch (fromTypeCode)
  1540. {
  1541. case DbgType_i8:
  1542. return true;
  1543. case DbgType_u8:
  1544. case DbgType_UChar:
  1545. case DbgType_UChar16:
  1546. return true;
  1547. }
  1548. break;
  1549. case DbgType_SChar32:
  1550. case DbgType_i32:
  1551. switch (fromTypeCode)
  1552. {
  1553. case DbgType_i8:
  1554. case DbgType_i16:
  1555. return true;
  1556. case DbgType_u8:
  1557. case DbgType_u16:
  1558. case DbgType_UChar:
  1559. case DbgType_UChar16:
  1560. return true;
  1561. }
  1562. break;
  1563. case DbgType_UChar32:
  1564. case DbgType_u32:
  1565. switch (fromTypeCode)
  1566. {
  1567. case DbgType_i8:
  1568. case DbgType_i16:
  1569. case DbgType_SChar:
  1570. case DbgType_SChar16:
  1571. return true;
  1572. case DbgType_u8:
  1573. case DbgType_u16:
  1574. case DbgType_u32:
  1575. case DbgType_UChar:
  1576. case DbgType_UChar16:
  1577. case DbgType_UChar32:
  1578. return true;
  1579. }
  1580. break;
  1581. case DbgType_i64:
  1582. switch (fromTypeCode)
  1583. {
  1584. case DbgType_i8:
  1585. case DbgType_i16:
  1586. case DbgType_i32:
  1587. case DbgType_i64:
  1588. case DbgType_SChar:
  1589. case DbgType_SChar16:
  1590. case DbgType_SChar32:
  1591. return true;
  1592. case DbgType_u8:
  1593. case DbgType_u16:
  1594. case DbgType_u32:
  1595. case DbgType_UChar:
  1596. case DbgType_UChar16:
  1597. case DbgType_UChar32:
  1598. return true;
  1599. }
  1600. break;
  1601. case DbgType_u64:
  1602. switch (fromTypeCode)
  1603. {
  1604. case DbgType_i8:
  1605. case DbgType_i16:
  1606. case DbgType_i32:
  1607. case DbgType_SChar:
  1608. case DbgType_SChar16:
  1609. case DbgType_SChar32:
  1610. return true;
  1611. case DbgType_u8:
  1612. case DbgType_u16:
  1613. case DbgType_u32:
  1614. case DbgType_UChar:
  1615. case DbgType_UChar32:
  1616. return true;
  1617. }
  1618. break;
  1619. case DbgType_Single:
  1620. switch (fromTypeCode)
  1621. {
  1622. case DbgType_i8:
  1623. case DbgType_i16:
  1624. case DbgType_i32:
  1625. return true;
  1626. case DbgType_u8:
  1627. case DbgType_u16:
  1628. case DbgType_u32:
  1629. case DbgType_UChar:
  1630. case DbgType_UChar32:
  1631. return true;
  1632. }
  1633. break;
  1634. case DbgType_Double:
  1635. switch (fromTypeCode)
  1636. {
  1637. case DbgType_i8:
  1638. case DbgType_i16:
  1639. case DbgType_i32:
  1640. case DbgType_i64:
  1641. case DbgType_SChar:
  1642. case DbgType_SChar16:
  1643. case DbgType_SChar32:
  1644. return true;
  1645. case DbgType_u8:
  1646. case DbgType_u16:
  1647. case DbgType_u32:
  1648. case DbgType_UChar:
  1649. case DbgType_UChar16:
  1650. case DbgType_UChar32:
  1651. return true;
  1652. case DbgType_Single:
  1653. return true;
  1654. }
  1655. break;
  1656. }
  1657. }
  1658. return false;
  1659. }
  1660. DbgTypedValue DbgExprEvaluator::Cast(BfAstNode* srcNode, const DbgTypedValue& typedVal, DbgType* toType, bool explicitCast, bool silentFail)
  1661. {
  1662. if (!typedVal)
  1663. return typedVal;
  1664. DbgType* fromType = typedVal.mType;
  1665. fromType = fromType->RemoveModifiers();
  1666. toType = toType->RemoveModifiers();
  1667. fromType = fromType->GetPrimaryType();
  1668. toType = toType->GetPrimaryType();
  1669. if ((toType->IsBfObject()) && (fromType->IsPointer()))
  1670. toType = toType->GetDbgModule()->GetPointerType(toType);
  1671. if (toType->IsPrimitiveType())
  1672. {
  1673. if (fromType->mTypeCode == toType->mTypeCode)
  1674. return typedVal;
  1675. if ((fromType->IsStruct()) || (fromType->IsEnum()))
  1676. {
  1677. if (fromType->mTypeParam != NULL)
  1678. {
  1679. DbgTypedValue underlyingTypedValue = typedVal;
  1680. underlyingTypedValue.mType = fromType->mTypeParam;
  1681. auto castedVal = Cast(srcNode, underlyingTypedValue, toType, explicitCast, true);
  1682. if (castedVal)
  1683. return castedVal;
  1684. }
  1685. }
  1686. }
  1687. if (fromType == toType)
  1688. return typedVal;
  1689. if ((fromType->mTypeCode == DbgType_Null) &&
  1690. (toType->mTypeCode == DbgType_Ptr))
  1691. {
  1692. DbgTypedValue val;
  1693. val.mPtr = typedVal.mPtr;
  1694. val.mType = toType;
  1695. return val;
  1696. }
  1697. auto curTypeInstance = GetCurrentType();
  1698. if ((fromType->IsCompositeType()) && ((toType->IsCompositeType() || (toType->IsInterface()))))
  1699. {
  1700. bool allowCast = false;
  1701. //TODO: Allow explicit interface casts on any object
  1702. //TODO: Insert cast checking code
  1703. int thisOffset = 0;
  1704. addr_target thisVal = typedVal.mSrcAddress;
  1705. if (TypeIsSubTypeOf(fromType, toType, &thisOffset, &thisVal))
  1706. {
  1707. allowCast = true;
  1708. }
  1709. else if ((explicitCast) && ((toType->IsInterface()) || (TypeIsSubTypeOf(toType, fromType, &thisOffset))))
  1710. {
  1711. thisOffset = -thisOffset;
  1712. allowCast = true;
  1713. }
  1714. if (fromType->IsBfPayloadEnum())
  1715. {
  1716. if (!allowCast)
  1717. {
  1718. for (auto member : fromType->mMemberList)
  1719. {
  1720. if (member->mType->Equals(toType))
  1721. {
  1722. allowCast = true;
  1723. break;
  1724. }
  1725. }
  1726. }
  1727. }
  1728. if (allowCast)
  1729. {
  1730. DbgTypedValue val;
  1731. //val.mPtr = typedVal.mPtr + thisOffset;
  1732. val.mInt64 = typedVal.mInt64;
  1733. val.mSrcAddress = thisVal + thisOffset;
  1734. val.mType = toType;
  1735. // Doing this allows us to modify a typed value that is tied to a register through its '[base]'
  1736. if ((typedVal.mRegNum != -1) && (val.mType->GetByteCount() == typedVal.mType->GetByteCount()))
  1737. val.mRegNum = typedVal.mRegNum;
  1738. return val;
  1739. }
  1740. }
  1741. // Payload discriminator
  1742. if ((fromType->IsBfPayloadEnum()) && (toType->IsInteger()))
  1743. {
  1744. intptr valAddr;
  1745. DbgType* valType;
  1746. DbgAddrType addrType = DbgAddrType_Value;
  1747. String findName = "$";
  1748. //BF_ASSERT(typedVal.mVariable != NULL);
  1749. if (typedVal.mVariable != NULL)
  1750. findName += typedVal.mVariable->mName;
  1751. findName += "$d";
  1752. if (mDebugTarget->GetValueByName(GetCurrentMethod(), findName, GetStackFrame(), &valAddr, &valType, &addrType))
  1753. {
  1754. return ReadTypedValue(srcNode, valType, valAddr, addrType);
  1755. }
  1756. }
  1757. // Optimized composite - probably stored in register
  1758. if ((toType->IsCompositeType()) && (fromType->IsInteger()) && (explicitCast))
  1759. {
  1760. if (toType->GetByteCount() <= 8)
  1761. {
  1762. DbgTypedValue val;
  1763. val.mType = toType;
  1764. val.mInt64 = typedVal.mInt64;
  1765. val.mSrcAddress = typedVal.mSrcAddress;
  1766. return val;
  1767. }
  1768. }
  1769. // Ptr -> const Ptr
  1770. if ((fromType->IsPointer()) && (toType->IsPointer()))
  1771. {
  1772. if (toType->mTypeParam->IsConst())
  1773. {
  1774. bool canCast = false;
  1775. auto primaryFrom = fromType->mTypeParam->GetPrimaryType();
  1776. auto primaryTo = toType->mTypeParam->mTypeParam->GetPrimaryType();
  1777. if ((primaryFrom->IsCompositeType()) || (primaryTo->IsCompositeType()))
  1778. {
  1779. if (primaryFrom == primaryTo)
  1780. canCast = true;
  1781. }
  1782. else if (primaryFrom->IsPrimitiveType())
  1783. {
  1784. canCast = primaryFrom->mTypeCode == primaryTo->mTypeCode;
  1785. }
  1786. if (canCast)
  1787. {
  1788. DbgTypedValue val = typedVal;
  1789. val.mType = toType;
  1790. return val;
  1791. }
  1792. }
  1793. }
  1794. if ((fromType->IsPointer()) && (fromType->mTypeParam->IsCompositeType()) &&
  1795. (toType->IsPointer()) && (toType->mTypeParam->IsCompositeType()))
  1796. {
  1797. auto fromInnerType = fromType->mTypeParam->RemoveModifiers();
  1798. auto toInnerType = toType->mTypeParam->RemoveModifiers();
  1799. /*DbgTypedValue fromVal;
  1800. fromVal.mType = fromInnerTytpe;
  1801. fromVal.mSrcAddress = typedVal.mPtr;
  1802. DbgTypedValue toVal = Cast(srcNode, fromVal, toInnerType, explicitCast, silentFail);
  1803. if (toVal)
  1804. {
  1805. // Back to pointer form
  1806. toVal.mType = toType;
  1807. toVal.mPtr = toVal.mSrcAddress;
  1808. toVal.mSrcAddress = 0;
  1809. }
  1810. return toVal;*/
  1811. bool allowCast = false;
  1812. //TODO: Allow explicit interface casts on any object
  1813. //TODO: Insert cast checking code
  1814. int thisOffset = 0;
  1815. addr_target thisVal = typedVal.mSrcAddress;
  1816. if (TypeIsSubTypeOf(fromInnerType, toInnerType, &thisOffset, &thisVal))
  1817. {
  1818. allowCast = true;
  1819. }
  1820. else if ((explicitCast) && ((toInnerType->IsInterface()) || (TypeIsSubTypeOf(toInnerType, fromInnerType, &thisOffset))))
  1821. {
  1822. thisOffset = -thisOffset;
  1823. allowCast = true;
  1824. }
  1825. if (allowCast)
  1826. {
  1827. DbgTypedValue toVal;
  1828. toVal.mType = toType;
  1829. toVal.mPtr = typedVal.mPtr + thisOffset;
  1830. toVal.mSrcAddress = 0;
  1831. return toVal;
  1832. }
  1833. }
  1834. // IFace -> object|IFace
  1835. if ((fromType->IsInterface()) ||
  1836. ((fromType->IsPointer()) && (fromType->mTypeParam->IsInterface())))
  1837. {
  1838. if (toType->IsBfObject())
  1839. {
  1840. DbgTypedValue val;
  1841. val.mPtr = typedVal.GetPointer();
  1842. val.mType = toType;
  1843. return val;
  1844. }
  1845. }
  1846. // Int|Ptr|Arr -> Int|Ptr|Arr
  1847. if (((fromType->IsInteger()) || (fromType->IsPointer()) || (fromType->IsSizedArray())) &&
  1848. ((toType->IsInteger()) || (toType->IsPointer()) || (toType->IsSizedArray())))
  1849. {
  1850. bool allowCast = explicitCast;
  1851. if (allowCast)
  1852. {
  1853. DbgTypedValue val;
  1854. if (toType->IsSizedArray())
  1855. val.mSrcAddress = typedVal.GetPointer();
  1856. else
  1857. val.mPtr = typedVal.GetPointer();
  1858. val.mType = toType;
  1859. return val;
  1860. }
  1861. }
  1862. // Enum -> Int
  1863. if ((((fromType->IsBfEnum()) || (fromType->IsEnum())) && (toType->IsInteger())) &&
  1864. ((explicitCast) || (fromType == curTypeInstance)))
  1865. {
  1866. DbgTypedValue result = typedVal;
  1867. result.mType = toType;
  1868. return result;
  1869. }
  1870. // Int -> Enum
  1871. if (((fromType->IsInteger()) && ((toType->IsBfEnum()) || (toType->IsEnum()))) &&
  1872. ((explicitCast) || (toType == curTypeInstance)))
  1873. {
  1874. DbgTypedValue result = typedVal;
  1875. result.mType = toType;
  1876. return result;
  1877. }
  1878. // TypedPrimitive -> Primitive
  1879. if ((fromType->IsTypedPrimitive()) && (toType->IsPrimitiveType()))
  1880. {
  1881. DbgTypedValue fromValue = typedVal;
  1882. fromValue.mType = fromType->GetBaseType();
  1883. return Cast(srcNode, fromValue, toType, explicitCast);
  1884. }
  1885. // TypedPrimitive -> TypedPrimitive
  1886. if ((fromType->IsTypedPrimitive()) && (toType->IsTypedPrimitive()))
  1887. {
  1888. DbgTypedValue fromValue = typedVal;
  1889. fromValue.mType = fromType->GetBaseType();
  1890. DbgTypedValue primTypedVal = Cast(srcNode, fromValue, toType->GetBaseType(), explicitCast, silentFail);
  1891. if (primTypedVal)
  1892. {
  1893. primTypedVal.mType = toType;
  1894. return primTypedVal;
  1895. }
  1896. }
  1897. // Primitive -> TypedPrimitive
  1898. if ((fromType->IsPrimitiveType()) && (toType->IsTypedPrimitive()))
  1899. {
  1900. DbgTypedValue primTypedVal = Cast(srcNode, typedVal, toType->GetBaseType(), true);
  1901. if (primTypedVal)
  1902. {
  1903. primTypedVal.mType = toType;
  1904. return primTypedVal;
  1905. }
  1906. }
  1907. if ((fromType->IsPrimitiveType()) && (toType->IsPrimitiveType()))
  1908. {
  1909. DbgTypeCode fromTypeCode = fromType->mTypeCode;
  1910. DbgTypeCode toTypeCode = toType->mTypeCode;
  1911. if ((toType->IsInteger()) && (fromType->IsIntegral()))
  1912. {
  1913. // Allow constant ints to be implicitly shrunk if they fit
  1914. if (typedVal.mIsLiteral)
  1915. {
  1916. int64 srcVal = typedVal.GetInt64();
  1917. /*if (toType->IsSigned())
  1918. {
  1919. int64 minVal = -(1LL << (8 * toType->mSize - 1));
  1920. int64 maxVal = (1LL << (8 * toType->mSize - 1)) - 1;
  1921. if ((srcVal >= minVal) && (srcVal <= maxVal))
  1922. explicitCast = true;
  1923. }
  1924. else if (toType->mSize == 8) // ulong
  1925. {
  1926. if (srcVal > 0)
  1927. explicitCast = true;
  1928. }
  1929. else
  1930. {
  1931. int64 minVal = 0;
  1932. int64 maxVal = (1LL << (8 * toType->mSize)) - 1;
  1933. if ((srcVal >= minVal) && (srcVal <= maxVal))
  1934. explicitCast = true;
  1935. }*/
  1936. if (toType->IsChar())
  1937. {
  1938. if (srcVal == 0)
  1939. explicitCast = true;
  1940. }
  1941. else if ((fromType->IsChar()) && (!toType->IsChar()))
  1942. {
  1943. // Never allow this
  1944. }
  1945. else if ((fromTypeCode == BfTypeCode_UInt64) && (srcVal < 0))
  1946. {
  1947. // There's nothing that this could fit into
  1948. }
  1949. else if (toType->IsSigned())
  1950. {
  1951. int64 minVal = -(1LL << (8 * toType->mSize - 1));
  1952. int64 maxVal = (1LL << (8 * toType->mSize - 1)) - 1;
  1953. if ((srcVal >= minVal) && (srcVal <= maxVal))
  1954. explicitCast = true;
  1955. }
  1956. else if (toType->mSize == 8) // ulong
  1957. {
  1958. if (srcVal >= 0)
  1959. explicitCast = true;
  1960. }
  1961. else
  1962. {
  1963. int64 minVal = 0;
  1964. int64 maxVal = (1LL << (8 * toType->mSize)) - 1;
  1965. if ((srcVal >= minVal) && (srcVal <= maxVal))
  1966. explicitCast = true;
  1967. }
  1968. }
  1969. }
  1970. DbgTypedValue result;
  1971. result.mType = toType;
  1972. if (((fromType->IsInteger()) || (fromType->IsChar())) &&
  1973. (toType->IsInteger()) || (toType->IsChar()))
  1974. {
  1975. result.mInt64 = typedVal.GetInt64();
  1976. if (explicitCast)
  1977. return result;
  1978. }
  1979. switch (toTypeCode)
  1980. {
  1981. case DbgType_u8:
  1982. case DbgType_UChar:
  1983. switch (fromTypeCode)
  1984. {
  1985. case DbgType_u8:
  1986. case DbgType_UChar:
  1987. return result;
  1988. }
  1989. break;
  1990. case DbgType_i16:
  1991. case DbgType_SChar16:
  1992. switch (fromTypeCode)
  1993. {
  1994. case DbgType_i8:
  1995. case DbgType_i16:
  1996. case DbgType_SChar:
  1997. case DbgType_SChar16:
  1998. return result;
  1999. case DbgType_u8:
  2000. case DbgType_UChar:
  2001. return result;
  2002. }
  2003. break;
  2004. case DbgType_u16:
  2005. case DbgType_UChar16:
  2006. switch (fromTypeCode)
  2007. {
  2008. case DbgType_i8:
  2009. case DbgType_SChar:
  2010. return result;
  2011. case DbgType_u8:
  2012. case DbgType_UChar:
  2013. return result;
  2014. }
  2015. break;
  2016. case DbgType_i32:
  2017. case DbgType_SChar32:
  2018. switch (fromTypeCode)
  2019. {
  2020. case DbgType_i8:
  2021. case DbgType_i16:
  2022. case DbgType_i32:
  2023. case DbgType_SChar:
  2024. case DbgType_SChar16:
  2025. case DbgType_SChar32:
  2026. return result;
  2027. case DbgType_u8:
  2028. case DbgType_u16:
  2029. case DbgType_UChar:
  2030. case DbgType_UChar16:
  2031. return result;
  2032. }
  2033. break;
  2034. case DbgType_UChar32:
  2035. case DbgType_u32:
  2036. switch (fromTypeCode)
  2037. {
  2038. case DbgType_i8:
  2039. case DbgType_i16:
  2040. case DbgType_SChar:
  2041. case DbgType_SChar16:
  2042. return result;
  2043. case DbgType_u8:
  2044. case DbgType_u16:
  2045. case DbgType_u32:
  2046. case DbgType_UChar:
  2047. case DbgType_UChar16:
  2048. case DbgType_UChar32:
  2049. return result;
  2050. }
  2051. break;
  2052. case DbgType_i64:
  2053. switch (fromTypeCode)
  2054. {
  2055. case DbgType_i8:
  2056. case DbgType_i16:
  2057. case DbgType_i32:
  2058. case DbgType_SChar:
  2059. case DbgType_SChar16:
  2060. case DbgType_SChar32:
  2061. return result;
  2062. case DbgType_u8:
  2063. case DbgType_u16:
  2064. case DbgType_u32:
  2065. case DbgType_UChar:
  2066. case DbgType_UChar16:
  2067. case DbgType_UChar32:
  2068. return result;
  2069. }
  2070. break;
  2071. case DbgType_u64:
  2072. switch (fromTypeCode)
  2073. {
  2074. case DbgType_i8:
  2075. case DbgType_i16:
  2076. case DbgType_i32:
  2077. case DbgType_SChar:
  2078. case DbgType_SChar16:
  2079. case DbgType_SChar32:
  2080. return result;
  2081. case DbgType_u8:
  2082. case DbgType_u16:
  2083. case DbgType_u32:
  2084. case DbgType_UChar:
  2085. case DbgType_UChar32:
  2086. return result;
  2087. }
  2088. break;
  2089. case DbgType_Single:
  2090. switch (fromTypeCode)
  2091. {
  2092. case DbgType_i8:
  2093. case DbgType_i16:
  2094. case DbgType_i32:
  2095. case DbgType_i64:
  2096. case DbgType_SChar:
  2097. case DbgType_SChar16:
  2098. case DbgType_SChar32:
  2099. result.mSingle = typedVal.GetInt64();
  2100. return result;
  2101. case DbgType_u8:
  2102. case DbgType_u16:
  2103. case DbgType_u32:
  2104. case DbgType_u64:
  2105. case DbgType_UChar:
  2106. case DbgType_UChar16:
  2107. case DbgType_UChar32:
  2108. result.mSingle = typedVal.GetInt64();
  2109. return result;
  2110. }
  2111. break;
  2112. case DbgType_Double:
  2113. switch (fromTypeCode)
  2114. {
  2115. case DbgType_i8:
  2116. case DbgType_i16:
  2117. case DbgType_i32:
  2118. case DbgType_i64:
  2119. case DbgType_SChar:
  2120. case DbgType_SChar16:
  2121. case DbgType_SChar32:
  2122. result.mDouble = typedVal.GetInt64();
  2123. return result;
  2124. case DbgType_u8:
  2125. case DbgType_u16:
  2126. case DbgType_u32:
  2127. case DbgType_u64:
  2128. case DbgType_UChar:
  2129. case DbgType_UChar16:
  2130. case DbgType_UChar32:
  2131. result.mDouble = typedVal.GetInt64();
  2132. return result;
  2133. case DbgType_Single:
  2134. result.mDouble = typedVal.mSingle;
  2135. return result;
  2136. }
  2137. break;
  2138. }
  2139. if (explicitCast)
  2140. {
  2141. if (toType->IsInteger())
  2142. {
  2143. if (typedVal.mType->IsInteger())
  2144. {
  2145. return result;
  2146. }
  2147. else if (typedVal.mType->IsFloat())
  2148. {
  2149. if (typedVal.mType->mTypeCode == DbgType_Single)
  2150. result.mInt64 = typedVal.mSingle;
  2151. else
  2152. result.mInt64 = (int64)typedVal.mDouble;
  2153. return result;
  2154. }
  2155. }
  2156. switch (toTypeCode)
  2157. {
  2158. case DbgType_Single:
  2159. switch (fromTypeCode)
  2160. {
  2161. case DbgType_i8:
  2162. case DbgType_i16:
  2163. case DbgType_i32:
  2164. case DbgType_SChar:
  2165. case DbgType_SChar16:
  2166. case DbgType_SChar32:
  2167. result.mSingle = (float)typedVal.GetInt64();
  2168. return result;
  2169. case DbgType_u8:
  2170. case DbgType_u16:
  2171. case DbgType_u32:
  2172. case DbgType_UChar:
  2173. case DbgType_UChar16:
  2174. case DbgType_UChar32:
  2175. result.mSingle = (float)typedVal.GetInt64();
  2176. return result;
  2177. case DbgType_Double:
  2178. result.mSingle = (float)typedVal.mDouble;
  2179. return result;
  2180. }
  2181. break;
  2182. }
  2183. }
  2184. }
  2185. if (fromType->mTypeCode == DbgType_TypeDef)
  2186. {
  2187. DbgTypedValue realTypedVal = typedVal;
  2188. realTypedVal.mType = fromType->mTypeParam;
  2189. return Cast(srcNode, realTypedVal, toType, explicitCast, silentFail);
  2190. }
  2191. if (toType->mTypeCode == DbgType_TypeDef)
  2192. return Cast(srcNode, typedVal, toType->mTypeParam, explicitCast, silentFail);
  2193. if (!silentFail)
  2194. {
  2195. auto language = GetLanguage();
  2196. const char* errStr = explicitCast ?
  2197. "Unable to cast '%s' to '%s'" :
  2198. "Unable to implicitly cast '%s' to '%s'";
  2199. Fail(StrFormat(errStr, fromType->ToString(language).c_str(), toType->ToString(language).c_str()), srcNode);
  2200. }
  2201. return DbgTypedValue();
  2202. }
  2203. bool DbgExprEvaluator::HasField(DbgType* curCheckType, const StringImpl& fieldName)
  2204. {
  2205. curCheckType = curCheckType->RemoveModifiers();
  2206. curCheckType = curCheckType->GetPrimaryType();
  2207. curCheckType->PopulateType();
  2208. for (auto checkMember : curCheckType->mMemberList)
  2209. {
  2210. if (checkMember->mName == NULL)
  2211. {
  2212. auto checkResult = HasField(checkMember->mType, fieldName);
  2213. if (checkResult)
  2214. return checkResult;
  2215. }
  2216. else if (checkMember->mName == fieldName)
  2217. return true;
  2218. }
  2219. for (auto baseTypeEntry : curCheckType->mBaseTypes)
  2220. {
  2221. auto baseType = baseTypeEntry->mBaseType;
  2222. auto result = HasField(baseType, fieldName);
  2223. if (result)
  2224. return result;
  2225. }
  2226. //if (wantsStatic)
  2227. {
  2228. // Look for statics in anonymous inner classes
  2229. for (auto checkSubType : curCheckType->mSubTypeList)
  2230. {
  2231. if (checkSubType->mTypeName == NULL)
  2232. {
  2233. auto result = HasField(checkSubType, fieldName);
  2234. if (result)
  2235. return result;
  2236. }
  2237. }
  2238. for (auto altType : curCheckType->mAlternates)
  2239. {
  2240. auto result = HasField(altType, fieldName);
  2241. if (result)
  2242. return result;
  2243. }
  2244. }
  2245. return false;
  2246. }
  2247. DbgTypedValue DbgExprEvaluator::DoLookupField(BfAstNode* targetSrc, DbgTypedValue target, DbgType* curCheckType, const StringImpl& fieldName, CPUStackFrame* stackFrame, bool allowImplicitThis)
  2248. {
  2249. if (mStackSearch != NULL)
  2250. {
  2251. if (mStackSearch->mIdentifier == targetSrc)
  2252. {
  2253. if (!mStackSearch->mSearchedTypes.Add(curCheckType))
  2254. return DbgTypedValue();
  2255. }
  2256. }
  2257. bool wantsStatic = (!target) || (target.mHasNoValue);
  2258. auto flavor = GetFlavor();
  2259. auto language = GetLanguage();
  2260. if (language != DbgLanguage_Beef)
  2261. {
  2262. // C allows static lookups by non-static member reference
  2263. wantsStatic = true;
  2264. }
  2265. curCheckType = curCheckType->RemoveModifiers();
  2266. curCheckType = curCheckType->GetPrimaryType();
  2267. curCheckType->PopulateType();
  2268. //BfLogDbgExpr("DoLookupField %s %s Priority=%d\n", fieldName.c_str(), curCheckType->mName, curCheckType->mPriority);
  2269. if ((curCheckType->mNeedsGlobalsPopulated) && ((curCheckType->IsNamespace()) || (curCheckType->IsRoot())))
  2270. {
  2271. // Global variables don't show up in any type declaration like static fields do, so we need to populate here
  2272. mDbgModule->PopulateTypeGlobals(curCheckType);
  2273. }
  2274. /*auto checkMember = curCheckType->mMemberList.mHead;
  2275. while (checkMember != NULL)*/
  2276. String findFieldName = fieldName;
  2277. if ((language == DbgLanguage_Beef) && (flavor == DbgFlavor_MS) && (target.mHasNoValue))
  2278. {
  2279. //if ((curCheckType->IsRoot()) || (curCheckType->IsNamespace()))
  2280. //findFieldName.insert(0, "bf__");
  2281. }
  2282. //for (auto checkMember : curCheckType->mMemberList)
  2283. auto nextMember = curCheckType->mMemberList.mHead;
  2284. while (nextMember != NULL)
  2285. {
  2286. auto checkMember = nextMember;
  2287. nextMember = checkMember->mNext;
  2288. if (checkMember->mName == NULL)
  2289. {
  2290. //TODO: Check inside anonymous type
  2291. DbgTypedValue innerTarget;
  2292. addr_target targetPtr = target.mSrcAddress;
  2293. if ((target.mType != NULL) && (target.mType->HasPointer()))
  2294. targetPtr = target.mPtr;
  2295. innerTarget.mSrcAddress = targetPtr + checkMember->mMemberOffset;
  2296. /*if (target.mPtr != 0)
  2297. innerTarget.mPtr = target.mPtr + checkMember->mMemberOffset;*/
  2298. innerTarget.mType = checkMember->mType;
  2299. auto checkResult = LookupField(targetSrc, innerTarget, fieldName);
  2300. if (checkResult)
  2301. return checkResult;
  2302. }
  2303. else if (checkMember->mName == findFieldName)
  2304. {
  2305. //BfLogDbgExpr(" Got Match\n");
  2306. //TODO:
  2307. /*if (field->mIsConst)
  2308. {
  2309. if (fieldInstance->mStaticValue == NULL)
  2310. mModule->ResolveConstField(curCheckType, field);
  2311. return DbgTypedValue(fieldInstance->mStaticValue, fieldInstance->mType);
  2312. }*/
  2313. //checkMember->mMemberOffset
  2314. if (mReferenceId != NULL)
  2315. {
  2316. if (curCheckType->IsRoot())
  2317. *mReferenceId = fieldName;
  2318. else if (curCheckType->IsEnum())
  2319. *mReferenceId = curCheckType->ToString();
  2320. else
  2321. *mReferenceId = curCheckType->ToString() + "." + fieldName;
  2322. }
  2323. if ((checkMember->mLocationLen == 0) && (checkMember->mIsStatic) && (!checkMember->mIsConst))
  2324. {
  2325. if (checkMember->mCompileUnit->mDbgModule->mDbgFlavor == DbgFlavor_MS)
  2326. {
  2327. if (curCheckType->mNeedsGlobalsPopulated)
  2328. {
  2329. mDbgModule->PopulateTypeGlobals(curCheckType);
  2330. return DoLookupField(targetSrc, target, curCheckType, fieldName, stackFrame, allowImplicitThis);
  2331. }
  2332. /*String memberName = curCheckType->ToString() + "::" + checkMember->mName;
  2333. mDbgModule->ParseSymbolData();
  2334. auto entry = mDbgModule->mSymbolNameMap.Find(memberName.c_str());
  2335. if (entry != NULL)
  2336. {
  2337. auto sym = entry->mValue;
  2338. int locLen = 1 + sizeof(addr_target);
  2339. uint8* locData = checkMember->mCompileUnit->mDbgModule->mAlloc.AllocBytes(locLen);
  2340. locData[0] = DW_OP_addr_noRemap;
  2341. *((addr_target*)(locData + 1)) = sym->mAddress;
  2342. checkMember->mLocationData = locData;
  2343. checkMember->mLocationLen = locLen;
  2344. }
  2345. else
  2346. {
  2347. BF_ASSERT("Static field not found" == 0);
  2348. }*/
  2349. }
  2350. else
  2351. {
  2352. continue;
  2353. //BF_FATAL("Unhandled");
  2354. //TODO: Is this needed anymore since we have 'primary types'?
  2355. /*auto altType = mDebugTarget->FindType(target.mType->ToString(true));
  2356. if (altType != NULL)
  2357. {
  2358. auto altChildNode = altType->mAlternates.mHead;
  2359. while ((altType != NULL) && (checkMember->mLocationLen == 0))
  2360. {
  2361. for (auto altMember : altType->mMemberList)
  2362. {
  2363. if (strcmp(altMember->mName, checkMember->mName))
  2364. {
  2365. if (altMember->mLocationData != NULL)
  2366. {
  2367. checkMember->mLinkName = altMember->mLinkName;
  2368. checkMember->mLocationData = altMember->mLocationData;
  2369. checkMember->mLocationLen = altMember->mLocationLen;
  2370. break;
  2371. }
  2372. }
  2373. }
  2374. if (altChildNode != NULL)
  2375. {
  2376. altType = altChildNode->mValue;
  2377. altChildNode = altChildNode->mNext;
  2378. }
  2379. else
  2380. break;
  2381. }
  2382. }*/
  2383. }
  2384. }
  2385. if (checkMember->mLocationLen != 0)
  2386. {
  2387. DbgAddrType addrType;
  2388. intptr valAddr = checkMember->mCompileUnit->mDbgModule->EvaluateLocation(NULL, checkMember->mLocationData, checkMember->mLocationLen, stackFrame, &addrType);
  2389. if ((language == DbgLanguage_Beef) && (checkMember->mType->IsConst()) && (checkMember->mType->mTypeParam->IsSizedArray()))
  2390. {
  2391. // We need an extra deref
  2392. valAddr = mDebugger->ReadMemory<addr_target>(valAddr);
  2393. }
  2394. if (checkMember->mIsConst)
  2395. addrType = DbgAddrType_Value;
  2396. return ReadTypedValue(targetSrc, checkMember->mType, valAddr, addrType);
  2397. }
  2398. else if (checkMember->mIsConst)
  2399. {
  2400. return ReadTypedValue(targetSrc, checkMember->mType, (uint64)&checkMember->mConstValue, DbgAddrType_Local);
  2401. }
  2402. else if (checkMember->mIsStatic)
  2403. {
  2404. if (curCheckType->mNeedsGlobalsPopulated)
  2405. {
  2406. mDbgModule->PopulateTypeGlobals(curCheckType);
  2407. nextMember = curCheckType->mMemberList.mHead;
  2408. continue;
  2409. }
  2410. Fail("Static variable not found, may have be optimized out", targetSrc);
  2411. //BfLogDbgExpr(" Static variable optimized out\n");
  2412. }
  2413. else
  2414. {
  2415. if ((allowImplicitThis) && (target.mPtr == 0))
  2416. target = GetThis();
  2417. if (!target)
  2418. {
  2419. Fail("Cannot reference a non-static member from a static method", targetSrc);
  2420. return DbgTypedValue();
  2421. }
  2422. addr_target targetPtr = target.mSrcAddress;
  2423. DbgTypedValue typedValue;
  2424. if (targetPtr == -1)
  2425. {
  2426. LookupSplatMember(target, fieldName);
  2427. typedValue = mResult;
  2428. mResult = DbgTypedValue();
  2429. }
  2430. else if ((targetPtr == 0) && (target.mPtr != 0) && (!target.mType->HasPointer()))
  2431. {
  2432. typedValue = ReadTypedValue(targetSrc, checkMember->mType, (uint64)&target.mPtr + checkMember->mMemberOffset, DbgAddrType_Local);
  2433. }
  2434. else
  2435. {
  2436. if (target.mType->HasPointer())
  2437. targetPtr = target.mPtr;
  2438. typedValue = ReadTypedValue(targetSrc, checkMember->mType, targetPtr + checkMember->mMemberOffset, DbgAddrType_Target);
  2439. }
  2440. if (checkMember->mBitSize != 0)
  2441. {
  2442. int expectedShift = (checkMember->mType->mSize * 8) - checkMember->mBitSize;
  2443. int shift = expectedShift - checkMember->mBitOffset;
  2444. typedValue.mUInt64 = typedValue.mUInt64 >> shift;
  2445. uint64 mask = 0;
  2446. for (int i = 0; i < checkMember->mBitSize; i++)
  2447. mask |= (1ULL << i);
  2448. typedValue.mUInt64 &= mask;
  2449. if ((checkMember->mType->IsSigned()) && ((typedValue.mUInt64 & (1LL << (checkMember->mBitSize - 1))) != 0))
  2450. {
  2451. // Sign extend
  2452. typedValue.mUInt64 |= ~mask;
  2453. }
  2454. }
  2455. return typedValue;
  2456. }
  2457. }
  2458. //checkMember = checkMember->mNext;
  2459. }
  2460. BF_ASSERT((mPropGet == NULL) && (mPropSet == NULL));
  2461. if (curCheckType->mMethodList.IsEmpty())
  2462. {
  2463. bool hasProps = false;
  2464. for (auto methodNameEntry : curCheckType->mMethodNameList)
  2465. {
  2466. const char* methodName = methodNameEntry->mName;
  2467. if (((methodName[0] == 'g') || (methodName[0] == 's')) &&
  2468. ((strncmp(methodName, "get__", 5) == 0) ||
  2469. (strncmp(methodName, "set__", 5) == 0)))
  2470. {
  2471. if (strcmp(methodName + 5, fieldName.c_str()) == 0)
  2472. {
  2473. curCheckType->mCompileUnit->mDbgModule->MapCompileUnitMethods(methodNameEntry->mCompileUnitId);
  2474. methodNameEntry->mCompileUnitId = -1;
  2475. }
  2476. }
  2477. }
  2478. }
  2479. for (int pass = 0; pass < 2; pass++)
  2480. {
  2481. for (auto method : curCheckType->mMethodList)
  2482. {
  2483. if (method->mName != NULL)
  2484. {
  2485. if (((method->mName[0] == 'g') || (method->mName[0] == 's')) &&
  2486. ((strncmp(method->mName, "get__", 5) == 0) ||
  2487. (strncmp(method->mName, "set__", 5) == 0)))
  2488. {
  2489. if (strcmp(method->mName + 5, fieldName.c_str()) == 0)
  2490. {
  2491. bool isGetter = method->mName[0] == 'g';
  2492. method->PopulateSubprogram();
  2493. if (fieldName.IsEmpty())
  2494. {
  2495. int expectedParams = (int)mIndexerValues.size();
  2496. if (!isGetter)
  2497. expectedParams++;
  2498. if (method->GetParamCount() != expectedParams)
  2499. continue;
  2500. }
  2501. DbgSubprogram*& subprogramRef = isGetter ? mPropGet : mPropSet;
  2502. if ((subprogramRef == NULL) ||
  2503. ((!method->mHasThis) && (wantsStatic)) ||
  2504. ((method->mHasThis) && (!wantsStatic || allowImplicitThis)))
  2505. {
  2506. if ((method->mHasThis) && (allowImplicitThis) && (!target))
  2507. {
  2508. target = GetThis();
  2509. }
  2510. if (subprogramRef == NULL)
  2511. subprogramRef = method;
  2512. else if ((method->mVTableLoc != -1) || (subprogramRef->mVTableLoc == -1))
  2513. subprogramRef = method;
  2514. }
  2515. }
  2516. }
  2517. }
  2518. }
  2519. bool loadedCompileUnit = false;
  2520. for (int methodIdx = 0; methodIdx < 2; methodIdx++)
  2521. {
  2522. auto method = (methodIdx == 0) ? mPropGet : mPropSet;
  2523. if (method == NULL)
  2524. continue;
  2525. if (method->mBlock.mLowPC == 0)
  2526. {
  2527. if (!curCheckType->mHasGlobalsPopulated)
  2528. mDbgModule->PopulateTypeGlobals(curCheckType);
  2529. for (auto methodNameEntry : curCheckType->mMethodNameList)
  2530. {
  2531. const char* methodName = methodNameEntry->mName;
  2532. if ((methodNameEntry->mCompileUnitId >= 0) && (strcmp(methodName, method->mName) == 0))
  2533. {
  2534. curCheckType->mCompileUnit->mDbgModule->MapCompileUnitMethods(methodNameEntry->mCompileUnitId);
  2535. loadedCompileUnit = true;
  2536. }
  2537. }
  2538. }
  2539. }
  2540. if (!loadedCompileUnit)
  2541. break;
  2542. }
  2543. // Found a result
  2544. if ((mPropGet != NULL) || (mPropSet != NULL))
  2545. {
  2546. mPropSrc = targetSrc;
  2547. mPropTarget = target;
  2548. return DbgTypedValue();
  2549. }
  2550. //TODO:
  2551. /*for (auto prop : curCheckType->mTypeDef->mProperties)
  2552. {
  2553. if (prop->mName == fieldName)
  2554. {
  2555. mModule->Fail("Cannot reference property");
  2556. return DbgTypedValue();
  2557. }
  2558. }*/
  2559. //curCheckType = curCheckType->GetBaseType();
  2560. for (auto baseTypeEntry : curCheckType->mBaseTypes)
  2561. {
  2562. auto baseType = baseTypeEntry->mBaseType;
  2563. DbgTypedValue baseTarget = target;
  2564. addr_target* ptrRef = NULL;
  2565. if ((baseTarget.mPtr != 0) && (target.mType->HasPointer()))
  2566. ptrRef = &baseTarget.mPtr;
  2567. else if (baseTarget.mSrcAddress != 0)
  2568. ptrRef = &baseTarget.mSrcAddress;
  2569. if (ptrRef != NULL)
  2570. {
  2571. if (baseTypeEntry->mVTableOffset != -1)
  2572. {
  2573. addr_target vtableAddr = mDebugger->ReadMemory<addr_target>(target.mPtr);
  2574. int32 virtThisOffset = mDebugger->ReadMemory<int32>(vtableAddr + baseTypeEntry->mVTableOffset * sizeof(int32));
  2575. *ptrRef += virtThisOffset;
  2576. }
  2577. else
  2578. *ptrRef += baseTypeEntry->mThisOffset;
  2579. }
  2580. //BF_ASSERT(baseTypeEntry->mVTableOffset == -1);
  2581. auto result = DoLookupField(targetSrc, baseTarget, baseType, fieldName, stackFrame, allowImplicitThis);
  2582. if (result)
  2583. return result;
  2584. }
  2585. if (wantsStatic)
  2586. {
  2587. // Look for statics in anonymous inner classes
  2588. for (auto checkSubType : curCheckType->mSubTypeList)
  2589. {
  2590. bool includeSubType = ((checkSubType->mTypeName == NULL) || (checkSubType->IsGlobalsContainer()));
  2591. if ((language == DbgLanguage_C) && (checkSubType->IsEnum()))
  2592. includeSubType = true;
  2593. if (includeSubType)
  2594. {
  2595. if ((checkSubType->IsGlobalsContainer()) && (checkSubType->mPriority <= DbgTypePriority_Normal))
  2596. continue;
  2597. auto rawCheckSubType = checkSubType->RemoveModifiers();
  2598. auto result = DoLookupField(targetSrc, DbgTypedValue(), rawCheckSubType, fieldName, stackFrame, false);
  2599. if (result)
  2600. return result;
  2601. }
  2602. }
  2603. //Turn alternates back on!
  2604. /*for (auto altType : curCheckType->mAlternates)
  2605. {
  2606. auto result = DoLookupField(targetSrc, DbgTypedValue(), altType, fieldName, stackFrame, false);
  2607. if (result)
  2608. return result;
  2609. }*/
  2610. }
  2611. return DbgTypedValue();
  2612. }
  2613. DbgTypedValue DbgExprEvaluator::LookupField(BfAstNode* targetSrc, DbgTypedValue target, const StringImpl& fieldName)
  2614. {
  2615. CPUStackFrame* stackFrame = GetStackFrame();
  2616. DbgType* curCheckType = NULL;
  2617. /*if (currentMethod != NULL)
  2618. curCheckType = currentMethod->mParentType;*/
  2619. DbgType* curMethodType = curCheckType;
  2620. if (target)
  2621. {
  2622. if (target.mType->IsPrimitiveType())
  2623. {
  2624. curCheckType = mDbgModule->GetPrimitiveStructType(target.mType->mTypeCode);
  2625. if (curCheckType == NULL)
  2626. return DbgTypedValue();
  2627. }
  2628. else
  2629. {
  2630. curCheckType = target.mType;
  2631. }
  2632. BF_ASSERT(curCheckType != NULL);
  2633. }
  2634. else if (target.mType != NULL)
  2635. curCheckType = target.mType;
  2636. if (curCheckType != NULL)
  2637. {
  2638. curCheckType = curCheckType->RemoveModifiers();
  2639. if (curCheckType->mTypeCode == DbgType_Ptr)
  2640. curCheckType = curCheckType->mTypeParam;
  2641. }
  2642. bool allowImplicitThis = false;
  2643. if (curCheckType == NULL)
  2644. {
  2645. auto currentMethod = GetCurrentMethod();
  2646. if (currentMethod != NULL)
  2647. {
  2648. curCheckType = currentMethod->GetTargetType();
  2649. allowImplicitThis = currentMethod->mHasThis;
  2650. }
  2651. }
  2652. //SetAndRestoreValue<DbgType*> prevTypeInstance(curMethodType, curCheckType);
  2653. if (curCheckType == NULL)
  2654. return DbgTypedValue();
  2655. return DoLookupField(targetSrc, target, curCheckType, fieldName, stackFrame, allowImplicitThis);
  2656. }
  2657. void DbgExprEvaluator::Visit(BfAstNode* node)
  2658. {
  2659. Fail("Invalid debug expression", node);
  2660. }
  2661. DbgTypedValue DbgExprEvaluator::ReadTypedValue(BfAstNode* targetSrc, DbgType* dbgType, uint64 valAddr, DbgAddrType addrType)
  2662. {
  2663. bool failedReadMemory = false;
  2664. if (addrType == DbgAddrType_Alias)
  2665. {
  2666. String findName = (const char*)valAddr;
  2667. if (targetSrc == NULL)
  2668. return DbgTypedValue();
  2669. auto source = targetSrc->GetSourceData();
  2670. auto bfParser = source->ToParser();
  2671. if (bfParser == NULL)
  2672. return DbgTypedValue();
  2673. auto identifierNode = source->mAlloc.Alloc<BfIdentifierNode>();
  2674. int srcStart = bfParser->AllocChars(findName.length());
  2675. memcpy((char*)source->mSrc + srcStart, findName.c_str(), findName.length());
  2676. identifierNode->Init(srcStart, srcStart, srcStart + findName.length());
  2677. SetAndRestoreValue<bool> prevIgnoreErrors(mIgnoreErrors, true);
  2678. auto result = LookupIdentifier(identifierNode);
  2679. if (result)
  2680. return result;
  2681. // Allow lookup in calling method if we are inlined (for mixin references)
  2682. auto currentMethod = GetCurrentMethod();
  2683. if ((currentMethod != NULL) && (currentMethod->mInlineeInfo != NULL))
  2684. {
  2685. SetAndRestoreValue<int> preCallstackIdx(mCallStackIdx);
  2686. mCallStackIdx++;
  2687. result = LookupIdentifier(identifierNode);
  2688. }
  2689. return result;
  2690. }
  2691. if (addrType == DbgAddrType_LocalSplat)
  2692. {
  2693. DbgTypedValue val;
  2694. val.mVariable = (DbgVariable*)valAddr;
  2695. val.mType = dbgType;
  2696. val.mSrcAddress = -1;
  2697. val.mIsReadOnly = true;
  2698. return val;
  2699. }
  2700. if (addrType == DbgAddrType_TargetDeref)
  2701. {
  2702. DbgTypedValue result = ReadTypedValue(targetSrc, dbgType, valAddr, DbgAddrType_Target);
  2703. if ((result.mType != NULL) && (result.mType->IsPointer()))
  2704. {
  2705. result.mType = result.mType->mTypeParam;
  2706. result.mSrcAddress = result.mPtr;
  2707. }
  2708. return result;
  2709. }
  2710. if (addrType == DbgAddrType_NoValue)
  2711. {
  2712. mPassInstance->Fail(StrFormat("No value", valAddr));
  2713. return DbgTypedValue();
  2714. }
  2715. else if (addrType == DbgAddrType_OptimizedOut)
  2716. {
  2717. mPassInstance->Fail(StrFormat("Optimized out", valAddr));
  2718. return DbgTypedValue();
  2719. }
  2720. bool hadRef = false;
  2721. DbgType* origDwType = dbgType;
  2722. while (true)
  2723. {
  2724. if (dbgType->mTypeCode == DbgType_Const)
  2725. {
  2726. dbgType = mDbgModule->GetInnerTypeOrVoid(dbgType);
  2727. }
  2728. else if ((dbgType->mTypeCode == DbgType_TypeDef) || (dbgType->mTypeCode == DbgType_Volatile))
  2729. {
  2730. dbgType = mDbgModule->GetInnerTypeOrVoid(dbgType);
  2731. }
  2732. else if ((dbgType->mTypeCode == DbgType_Ref) || (dbgType->mTypeCode == DbgType_RValueReference))
  2733. {
  2734. hadRef = true;
  2735. auto innerType = dbgType->mTypeParam;
  2736. if ((!innerType->IsCompositeType()) || (addrType == DbgAddrType_Target))
  2737. {
  2738. if (addrType == DbgAddrType_Target)
  2739. valAddr = mDebugger->ReadMemory<addr_target>(valAddr);
  2740. if (addrType == DbgAddrType_Register)
  2741. {
  2742. auto registers = GetRegisters();
  2743. valAddr = registers->mIntRegsArray[valAddr];
  2744. }
  2745. //valIsAddr = true;
  2746. addrType = DbgAddrType_Target;
  2747. //local = false;
  2748. }
  2749. else
  2750. {
  2751. //local = false;
  2752. //valIsAddr = true;
  2753. if (addrType == DbgAddrType_Register)
  2754. {
  2755. auto registers = GetRegisters();
  2756. valAddr = registers->mIntRegsArray[valAddr];
  2757. }
  2758. addrType = DbgAddrType_Target;
  2759. }
  2760. dbgType = dbgType->mTypeParam;
  2761. }
  2762. else
  2763. break;
  2764. }
  2765. dbgType = dbgType->GetPrimaryType();
  2766. if (dbgType->GetByteCount() == 0)
  2767. {
  2768. DbgTypedValue result;
  2769. result.mType = dbgType;
  2770. return result;
  2771. }
  2772. if (dbgType->mTypeCode == DbgType_Bitfield)
  2773. {
  2774. DbgType* underlyingType = dbgType->mTypeParam;
  2775. DbgTypedValue result = ReadTypedValue(targetSrc, dbgType->mTypeParam, valAddr, addrType);
  2776. result.mType = dbgType;
  2777. auto dbgBitfieldType = (DbgBitfieldType*)dbgType;
  2778. result.mUInt64 = result.mUInt64 >> dbgBitfieldType->mPosition;
  2779. uint64 mask = ((uint64)1 << dbgBitfieldType->mLength) - 1;
  2780. result.mUInt64 &= mask;
  2781. if ((underlyingType->IsSigned()) && ((result.mUInt64 & (1LL << (dbgBitfieldType->mLength - 1))) != 0))
  2782. {
  2783. // Sign extend
  2784. result.mUInt64 |= ~mask;
  2785. }
  2786. return result;
  2787. }
  2788. bool local = addrType == DbgAddrType_Local;
  2789. bool valIsAddr = (addrType == DbgAddrType_Local) || (addrType == DbgAddrType_Target);
  2790. DbgTypedValue result;
  2791. result.mType = origDwType;
  2792. if (addrType == DbgAddrType_Register)
  2793. {
  2794. result.mRegNum = (int)valAddr;
  2795. auto registers = GetRegisters();
  2796. if (result.mRegNum < CPURegisters::kNumIntRegs)
  2797. result.mUInt64 = registers->mIntRegsArray[result.mRegNum];
  2798. else if ((result.mRegNum >= CPUReg_XMMREG_FIRST) && (result.mRegNum <= CPUReg_XMMREG_LAST))
  2799. {
  2800. auto dwType = origDwType->RemoveModifiers();
  2801. if (dwType->IsTypedPrimitive())
  2802. dwType = dwType->GetUnderlyingType();
  2803. if (dwType->mTypeCode == DbgType_Single)
  2804. result.mSingle = *(float*)((float*)registers->mXmmRegsArray + (result.mRegNum - CPUReg_XMMREG_FIRST));
  2805. else if (dwType->mTypeCode == DbgType_Double)
  2806. result.mDouble = *(double*)((float*)registers->mXmmRegsArray + (result.mRegNum - CPUReg_XMMREG_FIRST));
  2807. else
  2808. BF_ASSERT("Not implemented" == 0);
  2809. }
  2810. auto primaryType = result.mType->GetPrimaryType();
  2811. result.mType = primaryType;
  2812. // In release builds, VC will place int-sized structs into a single register. This code was breaking that.
  2813. /*if ((primaryType->IsCompositeType()) && (!primaryType->IsTypedPrimitive()))
  2814. {
  2815. result.mSrcAddress = result.mPtr;
  2816. result.mPtr = 0;
  2817. }*/
  2818. return result;
  2819. }
  2820. if (dbgType->mTypeCode == DbgType_Bitfield)
  2821. dbgType = dbgType->mTypeParam;
  2822. switch (dbgType->mTypeCode)
  2823. {
  2824. case DbgType_Void:
  2825. break;
  2826. case DbgType_Bool:
  2827. case DbgType_i8:
  2828. case DbgType_u8:
  2829. case DbgType_SChar:
  2830. case DbgType_UChar:
  2831. if (valIsAddr)
  2832. result.mInt8 = mDebugger->ReadMemory<int8>(valAddr, local, &failedReadMemory);
  2833. else
  2834. result.mUInt8 = (uint8)valAddr;
  2835. break;
  2836. case DbgType_i16:
  2837. case DbgType_u16:
  2838. case DbgType_SChar16:
  2839. case DbgType_UChar16:
  2840. if (valIsAddr)
  2841. result.mInt16 = mDebugger->ReadMemory<int16>(valAddr, local, &failedReadMemory);
  2842. else
  2843. result.mUInt16 = (uint16)valAddr;
  2844. break;
  2845. case DbgType_i32:
  2846. case DbgType_u32:
  2847. case DbgType_SChar32:
  2848. case DbgType_UChar32:
  2849. if (valIsAddr)
  2850. result.mInt32 = mDebugger->ReadMemory<int32>(valAddr, local, &failedReadMemory);
  2851. else
  2852. result.mUInt32 = (uint32)valAddr;
  2853. break;
  2854. case DbgType_i64:
  2855. case DbgType_u64:
  2856. if (valIsAddr)
  2857. result.mInt64 = mDebugger->ReadMemory<int64>(valAddr, local, &failedReadMemory);
  2858. else
  2859. result.mUInt64 = (uint64)valAddr;
  2860. break;
  2861. case DbgType_Single:
  2862. result.mSingle = mDebugger->ReadMemory<float>(valAddr, local, &failedReadMemory);
  2863. break;
  2864. case DbgType_Double:
  2865. result.mDouble = mDebugger->ReadMemory<double>(valAddr, local, &failedReadMemory);
  2866. break;
  2867. case DbgType_Struct:
  2868. case DbgType_Class:
  2869. case DbgType_Union:
  2870. case DbgType_SizedArray:
  2871. if (((dbgType->IsTypedPrimitive()) || (local)) && (dbgType->GetByteCount() <= 8))
  2872. {
  2873. mDebugger->ReadMemory(valAddr, dbgType->GetByteCount(), &result.mInt64, local);
  2874. result.mSrcAddress = (addr_target)valAddr;
  2875. }
  2876. else
  2877. {
  2878. BF_ASSERT(!local);
  2879. if (hadRef)
  2880. result.mPtr = (addr_target)valAddr;
  2881. else
  2882. result.mSrcAddress = (addr_target)valAddr;
  2883. }
  2884. //result.mPtr = (addr_target)valAddr;
  2885. break;
  2886. //TODO: Why was it treated as a pointer
  2887. //case DbgType_SizedArray:
  2888. case DbgType_Ptr:
  2889. if (valIsAddr)
  2890. result.mPtr = mDebugger->ReadMemory<addr_target>(valAddr, local, &failedReadMemory);
  2891. else
  2892. result.mPtr = valAddr;
  2893. break;
  2894. case DbgType_Enum:
  2895. result = ReadTypedValue(targetSrc, dbgType->mTypeParam, valAddr, addrType);
  2896. if (result)
  2897. result.mType = dbgType;
  2898. break;
  2899. case DbgType_Subroutine:
  2900. {
  2901. auto funcPtr = result.mPtr;
  2902. String symbolName;
  2903. addr_target offset;
  2904. DbgModule* dwarf;
  2905. if (mDebugTarget->FindSymbolAt(funcPtr, &symbolName, &offset, &dwarf))
  2906. {
  2907. #ifdef BF_DBG_32
  2908. if ((symbolName.length() > 0) && (symbolName[0] == '_'))
  2909. symbolName = symbolName.Substring(1);
  2910. #endif
  2911. static String demangledName;
  2912. demangledName = BfDemangler::Demangle(symbolName, dbgType->GetLanguage());
  2913. DbgTypedValue result;
  2914. result.mCharPtr = demangledName.c_str();
  2915. }
  2916. else
  2917. {
  2918. result.mCharPtr = NULL;
  2919. }
  2920. }
  2921. break;
  2922. default:
  2923. if (mPassInstance != NULL)
  2924. mPassInstance->Fail("Invalid data type");
  2925. }
  2926. if ((!local) && (valIsAddr))
  2927. {
  2928. result.mSrcAddress = valAddr;
  2929. }
  2930. if ((failedReadMemory) && (!mValidateOnly))
  2931. {
  2932. if (mPassInstance == NULL)
  2933. return DbgTypedValue();
  2934. if (addrType == DbgAddrType_NoValue)
  2935. mPassInstance->Fail("No value");
  2936. else if ((valAddr == 0) && (local))
  2937. mPassInstance->Fail("Optimized out");
  2938. else if (!mBlockedSideEffects)
  2939. mPassInstance->Fail(StrFormat("Failed to read from address %s", EncodeDataPtr(valAddr, true).c_str()));
  2940. }
  2941. return result;
  2942. }
  2943. bool DbgExprEvaluator::CheckTupleCreation(addr_target receiveAddr, BfAstNode* targetSrc, DbgType* tupleType, const BfSizedArray<BfExpression*>& argValues, BfSizedArray<BfTupleNameNode*>* names)
  2944. {
  2945. int memberIdx = 0;
  2946. tupleType = tupleType->RemoveModifiers();
  2947. tupleType = tupleType->GetPrimaryType();
  2948. for (auto member : tupleType->mMemberList)
  2949. {
  2950. if (member->mIsStatic)
  2951. continue;
  2952. DbgTypedValue receivingValue;
  2953. receivingValue.mSrcAddress = receiveAddr + member->mMemberOffset;
  2954. receivingValue.mType = member->mType;
  2955. if (memberIdx < argValues.size())
  2956. {
  2957. if ((names != NULL) && (memberIdx < names->size()) && ((*names)[memberIdx] != NULL))
  2958. {
  2959. String name;
  2960. if (auto tupleName = BfNodeDynCast<BfTupleNameNode>((*names)[memberIdx]))
  2961. name = tupleName->mNameNode->ToString();
  2962. else
  2963. name = (*names)[memberIdx]->ToString();
  2964. if ((member->mName != NULL) && (!isdigit(member->mName[0])) && (name != member->mName))
  2965. {
  2966. Fail(StrFormat("Name '%s' does not match expect name '%s'", name.c_str(), member->mName), (*names)[memberIdx]);
  2967. }
  2968. }
  2969. StoreValue(receivingValue, argValues[memberIdx]);
  2970. }
  2971. else
  2972. {
  2973. Fail("Not enough arguments", targetSrc);
  2974. }
  2975. memberIdx++;
  2976. }
  2977. if (memberIdx < argValues.size())
  2978. {
  2979. Fail("Too many arguments", argValues[memberIdx]);
  2980. }
  2981. return false;
  2982. }
  2983. DbgTypedValue DbgExprEvaluator::CheckEnumCreation(BfAstNode* targetSrc, DbgType* enumType, const StringImpl& caseName, const BfSizedArray<BfExpression*>& argValues)
  2984. {
  2985. BF_ASSERT(enumType->IsBfPayloadEnum());
  2986. addr_target receiveAddr = 0;
  2987. if (mReceivingValue != NULL)
  2988. {
  2989. receiveAddr = mReceivingValue->mSrcAddress;
  2990. }
  2991. if (receiveAddr == 0)
  2992. {
  2993. Fail("Address for enum cannot be inferred", targetSrc);
  2994. return DbgTypedValue();
  2995. }
  2996. enumType = enumType->RemoveModifiers();
  2997. enumType = enumType->GetPrimaryType();
  2998. int caseNum = -1;
  2999. DbgVariable* matchedMember = NULL;
  3000. for (auto member : enumType->mMemberList)
  3001. {
  3002. if ((member->mName[0] == '_') && (member->mName[1] >= '0') && (member->mName[1] <= '9'))
  3003. {
  3004. for (int i = 1; true; i++)
  3005. {
  3006. if (member->mName[i] == '_')
  3007. {
  3008. if (caseName == member->mName + i + 1)
  3009. {
  3010. caseNum = atoi(member->mName + 1);
  3011. matchedMember = member;
  3012. }
  3013. break;
  3014. }
  3015. else if (member->mName[i] == 0)
  3016. break;
  3017. }
  3018. }
  3019. if (strcmp(member->mName, "__bftag") == 0)
  3020. {
  3021. if (mReceivingValue != NULL)
  3022. mReceivingValue = NULL;
  3023. mDebugger->WriteMemory(receiveAddr + member->mMemberOffset, &caseNum, member->mType->GetByteCount());
  3024. CheckTupleCreation(receiveAddr + matchedMember->mMemberOffset, targetSrc, matchedMember->mType, argValues, NULL);
  3025. DbgTypedValue typedValue;
  3026. typedValue.mType = enumType;
  3027. typedValue.mSrcAddress = receiveAddr;
  3028. return typedValue;
  3029. }
  3030. }
  3031. return DbgTypedValue();
  3032. }
  3033. bool DbgExprEvaluator::IsAutoCompleteNode(BfAstNode* node, int lengthAdd)
  3034. {
  3035. if (node == NULL)
  3036. return false;
  3037. return ((mCursorPos >= node->GetSrcStart()) && (mCursorPos < node->GetSrcEnd() + lengthAdd));
  3038. }
  3039. void DbgExprEvaluator::AutocompleteCheckType(BfTypeReference* typeReference)
  3040. {
  3041. if (!IsAutoCompleteNode(typeReference))
  3042. return;
  3043. if (auto namedTypeRef = BfNodeDynCast <BfNamedTypeReference>(typeReference))
  3044. {
  3045. String filter = namedTypeRef->ToString();
  3046. mAutoComplete->mInsertStartIdx = namedTypeRef->GetSrcStart();
  3047. mAutoComplete->mInsertEndIdx = namedTypeRef->GetSrcEnd();
  3048. AutocompleteAddTopLevelTypes(filter);
  3049. }
  3050. else if (auto qualifiedTypeRef = BfNodeDynCast<BfQualifiedTypeReference>(typeReference))
  3051. {
  3052. if (IsAutoCompleteNode(qualifiedTypeRef->mLeft))
  3053. {
  3054. AutocompleteCheckType(qualifiedTypeRef->mLeft);
  3055. return;
  3056. }
  3057. auto dbgType = ResolveTypeRef(qualifiedTypeRef->mLeft);
  3058. if (dbgType != NULL)
  3059. {
  3060. String filter;
  3061. if (qualifiedTypeRef->mRight != NULL)
  3062. {
  3063. filter = qualifiedTypeRef->mRight->ToString();
  3064. mAutoComplete->mInsertStartIdx = qualifiedTypeRef->mRight->GetSrcStart();
  3065. mAutoComplete->mInsertEndIdx = qualifiedTypeRef->mRight->GetSrcEnd();
  3066. }
  3067. else
  3068. {
  3069. mAutoComplete->mInsertStartIdx = qualifiedTypeRef->mDot->GetSrcEnd();
  3070. mAutoComplete->mInsertEndIdx = qualifiedTypeRef->mDot->GetSrcEnd();
  3071. }
  3072. AutocompleteAddMembers(dbgType, false, false, filter);
  3073. }
  3074. }
  3075. else if (auto elementedTypeRef = BfNodeDynCast<BfElementedTypeRef>(typeReference))
  3076. {
  3077. AutocompleteCheckType(elementedTypeRef->mElementType);
  3078. }
  3079. }
  3080. void DbgExprEvaluator::AutocompleteAddTopLevelTypes(const StringImpl& filter)
  3081. {
  3082. GetNamespaceSearch();
  3083. for (auto usingNamespace : mNamespaceSearch)
  3084. {
  3085. usingNamespace = usingNamespace->GetPrimaryType();
  3086. AutocompleteAddMembers(usingNamespace, true, false, filter);
  3087. }
  3088. mDbgModule->ParseGlobalsData();
  3089. int methodEntryCount = 0;
  3090. //for (auto compileUnit : mDbgModule->mCompileUnits)
  3091. for (int compileIdx = 0; compileIdx < (int)mDbgModule->mCompileUnits.size(); compileIdx++)
  3092. {
  3093. auto compileUnit = mDbgModule->mCompileUnits[compileIdx];
  3094. if (mDbgCompileUnit == NULL)
  3095. continue;
  3096. if ((compileUnit->mLanguage != DbgLanguage_Unknown) && (compileUnit->mLanguage != mDbgCompileUnit->mLanguage))
  3097. continue;
  3098. AutocompleteAddMembers(compileUnit->mGlobalType, true, false, filter);
  3099. /*for (auto dwMethod : compileUnit->mGlobalType.mMethodList)
  3100. {
  3101. if (dwMethod->mName != NULL)
  3102. {
  3103. methodEntryCount++;
  3104. mAutoComplete->AddEntry(AutoCompleteEntry("method", dwMethod->mName), filter);
  3105. }
  3106. }*/
  3107. }
  3108. auto language = GetLanguage();
  3109. if (language == DbgLanguage_Beef)
  3110. {
  3111. for (auto primType : mDbgModule->mBfPrimitiveTypes)
  3112. {
  3113. if (primType != NULL)
  3114. mAutoComplete->AddEntry(AutoCompleteEntry("valuetype", primType->mName), filter);
  3115. }
  3116. char* primNames[2] = { "int", "uint" };
  3117. for (auto primName : primNames)
  3118. mAutoComplete->AddEntry(AutoCompleteEntry("valuetype", primName), filter);
  3119. }
  3120. else
  3121. {
  3122. for (auto primType : mDbgModule->mCPrimitiveTypes)
  3123. {
  3124. if (primType != NULL)
  3125. mAutoComplete->AddEntry(AutoCompleteEntry("valuetype", primType->mName), filter);
  3126. }
  3127. }
  3128. int typeEntrCount = 0;
  3129. //TODO: Does this get everything?
  3130. /*for (auto dwTypeEntry : mDbgModule->mTypeMap)
  3131. {
  3132. auto dbgType = dwTypeEntry->mValue;
  3133. if ((dbgType->mParent == NULL) && (dbgType->mTypeParam == NULL) &&
  3134. (dbgType->mTypeCode != DbgType_Ptr) && (dbgType->mTypeCode != DbgType_Ref))
  3135. {
  3136. String typeStr = dbgType->ToString();
  3137. if (typeStr[typeStr.length() - 1] == '^')
  3138. continue;
  3139. mAutoComplete->AddEntry(AutoCompleteEntry("type", typeStr), filter);
  3140. typeEntrCount++;
  3141. }
  3142. }*/
  3143. }
  3144. DbgTypedValue DbgExprEvaluator::DoLookupIdentifier(BfAstNode* identifierNode, bool ignoreInitialError, bool* hadError)
  3145. {
  3146. if (!mDebugger->mIsRunning)
  3147. return DbgTypedValue();
  3148. auto qualifiedNameNode = BfNodeDynCast<BfQualifiedNameNode>(identifierNode);
  3149. if (qualifiedNameNode != NULL)
  3150. {
  3151. LookupQualifiedName(qualifiedNameNode, ignoreInitialError, hadError);
  3152. auto qualifiedResult = mResult;
  3153. mResult = DbgTypedValue();
  3154. return qualifiedResult;
  3155. }
  3156. String findName = identifierNode->ToString();
  3157. if ((findName.StartsWith('$')) && (findName != "$prim"))
  3158. {
  3159. if (IsAutoCompleteNode(identifierNode))
  3160. {
  3161. String filter = identifierNode->ToString();
  3162. const char* identifiers[] =
  3163. {
  3164. "$ThreadId", "$ThreadName", "$TargetName", "$TargetPath", "$ModuleName", "$ModulePath",
  3165. "$HitCount", "$ProcessId"
  3166. };
  3167. for (int idx = 0; idx < BF_ARRAY_COUNT(identifiers); idx++)
  3168. mAutoComplete->AddEntry(AutoCompleteEntry("dbg", identifiers[idx]), filter);
  3169. mAutoComplete->mInsertStartIdx = identifierNode->GetSrcStart();
  3170. mAutoComplete->mInsertEndIdx = identifierNode->GetSrcEnd();
  3171. }
  3172. if (findName == "$this")
  3173. return GetThis();
  3174. else if (findName == "$ThreadId")
  3175. return GetInt(mDebugger->mActiveThread->mThreadId);
  3176. else if (findName == "$ThreadName")
  3177. return GetString(mDebugger->mActiveThread->mName);
  3178. else if (findName == "$TargetName")
  3179. return GetString(GetFileName(mDebugTarget->mTargetPath));
  3180. else if (findName == "LaunchName")
  3181. return GetString(GetFileName(mDebugTarget->mLaunchBinary->mFilePath));
  3182. else if (findName == "$TargetPath")
  3183. return GetString(mDebugTarget->mTargetPath);
  3184. else if (findName == "$ModuleName")
  3185. return GetString(GetFileName(mDbgModule->mFilePath));
  3186. else if (findName == "$ModulePath")
  3187. return GetString(mDbgModule->mFilePath);
  3188. else if (findName == "$HitCount")
  3189. {
  3190. if (mDebugger->mActiveBreakpoint != NULL)
  3191. return GetInt(mDebugger->mActiveBreakpoint->GetHeadBreakpoint()->mHitCount);
  3192. return GetInt(0);
  3193. }
  3194. else if (findName == "$BreakpointCondition")
  3195. {
  3196. if ((mDebugger->mActiveBreakpoint != NULL) && (mDebugger->mActiveBreakpoint->mCondition != NULL))
  3197. return GetString(mDebugger->mActiveBreakpoint->GetHeadBreakpoint()->mCondition->mExpr);
  3198. return GetString("");
  3199. }
  3200. else if (findName == "$ProcessId")
  3201. return GetInt(mDebugger->mProcessInfo.dwProcessId);
  3202. bool mayBeRegister = true;
  3203. for (int i = 1; i < findName.length(); i++)
  3204. if (findName[i] == '$')
  3205. mayBeRegister = false;
  3206. if (mayBeRegister)
  3207. {
  3208. DbgTypedValue val = GetRegister(findName.Substring(1));
  3209. if (val)
  3210. return val;
  3211. }
  3212. }
  3213. DbgTypedValue result;
  3214. if (mExplicitThis)
  3215. {
  3216. if ((mExplicitThis.mSrcAddress == -1) && ((DbgVariable*)mExplicitThis.mVariable != NULL))
  3217. {
  3218. mResult = DbgTypedValue();
  3219. LookupSplatMember(mExplicitThis, findName);
  3220. result = mResult;
  3221. mResult = DbgTypedValue();
  3222. }
  3223. else if (!result)
  3224. {
  3225. mExplicitThis.mType = mExplicitThis.mType->RemoveModifiers();
  3226. result = LookupField(identifierNode, mExplicitThis, findName);
  3227. }
  3228. if (result)
  3229. {
  3230. if (mExplicitThisExpr != NULL)
  3231. mDeferredInsertExplicitThisVector.push_back(NodeReplaceRecord(identifierNode, mCurChildRef));
  3232. return result;
  3233. }
  3234. }
  3235. CPUStackFrame* stackFrame = GetStackFrame();
  3236. auto language = GetLanguage();
  3237. intptr valAddr;
  3238. DbgType* valType;
  3239. DbgAddrType addrType = DbgAddrType_None;
  3240. if (IsAutoCompleteNode(identifierNode))
  3241. {
  3242. String filter = identifierNode->ToString();
  3243. DbgType* dbgType = NULL;
  3244. auto currentMethod = GetCurrentMethod();
  3245. auto thisVal = GetThis();
  3246. auto targetType = thisVal.mType;
  3247. if (currentMethod != NULL)
  3248. {
  3249. if (targetType != NULL)
  3250. dbgType = targetType;
  3251. else if (!thisVal)
  3252. dbgType = currentMethod->GetTargetType();
  3253. }
  3254. Array<String> capturedNames;
  3255. Array<DbgType*> capturedTypes;
  3256. mDebugTarget->mCapturedNamesPtr = &capturedNames;
  3257. mDebugTarget->mCapturedTypesPtr = &capturedTypes;
  3258. {
  3259. mDebugTarget->GetValueByName(GetCurrentMethod(), "*", stackFrame, &valAddr, &valType, &addrType);
  3260. }
  3261. mDebugTarget->mCapturedNamesPtr = NULL;
  3262. mDebugTarget->mCapturedTypesPtr = NULL;
  3263. auto language = GetLanguage();
  3264. BF_ASSERT(capturedTypes.size() == capturedNames.size());
  3265. {
  3266. //for (auto capturedName : capturedNames)
  3267. for (int i = 0; i < (int)capturedNames.size(); i++)
  3268. {
  3269. const String capturedName = capturedNames[i];
  3270. if (language == DbgLanguage_Beef)
  3271. {
  3272. // Don't put splats
  3273. if ((capturedName.length() > 0) && (capturedName[0] == '$'))
  3274. continue;
  3275. }
  3276. //TODO: Show the type icon
  3277. mAutoComplete->AddEntry(AutoCompleteEntry(GetTypeName(capturedTypes[i]), capturedNames[i]), filter);
  3278. }
  3279. }
  3280. if (!mSubjectExpr.IsEmpty())
  3281. {
  3282. mAutoComplete->AddEntry(AutoCompleteEntry("valuetype", "_"), filter);
  3283. }
  3284. if (dbgType != NULL)
  3285. {
  3286. dbgType = dbgType->RemoveModifiers();
  3287. if (dbgType->IsPointerOrRef())
  3288. {
  3289. dbgType = dbgType->mTypeParam;
  3290. dbgType = dbgType->RemoveModifiers();
  3291. }
  3292. if (dbgType->mIsDeclaration)
  3293. dbgType = dbgType->GetPrimaryType();
  3294. bool wantsStatic = true;
  3295. bool wantsNonStatic = currentMethod->mHasThis;
  3296. // In Beef, we can only access statics by class name
  3297. if (dbgType->GetLanguage() != DbgLanguage_Beef)
  3298. wantsStatic = !wantsNonStatic;
  3299. AutocompleteAddMembers(dbgType, wantsStatic, wantsNonStatic, filter);
  3300. if (currentMethod != NULL)
  3301. {
  3302. if (language == DbgLanguage_C)
  3303. {
  3304. // C++ closures
  3305. auto currentMethod = GetCurrentMethod();
  3306. if (currentMethod != NULL)
  3307. {
  3308. if (strstr(currentMethod->mName, "operator()") != NULL)
  3309. {
  3310. if (mDebugTarget->GetValueByName(currentMethod, "this", stackFrame, &valAddr, &valType, &addrType))
  3311. {
  3312. valType = valType->RemoveModifiers();
  3313. if (valType->IsPointer())
  3314. valType = valType->mTypeParam;
  3315. valType = valType->RemoveModifiers();
  3316. AutocompleteAddMembers(valType, true, true, filter, true);
  3317. }
  3318. }
  3319. }
  3320. }
  3321. else
  3322. {
  3323. // If in a Beef closure...
  3324. if (mDebugTarget->GetValueByName(currentMethod, "__closure", stackFrame, &valAddr, &valType, &addrType))
  3325. {
  3326. valType = valType->RemoveModifiers();
  3327. if (valType->IsPointer())
  3328. valType = valType->mTypeParam;
  3329. AutocompleteAddMembers(valType, true, true, filter, true);
  3330. }
  3331. }
  3332. auto targetType = currentMethod->GetTargetType();
  3333. if ((targetType != dbgType) && (targetType != NULL))
  3334. {
  3335. AutocompleteAddMembers(targetType, wantsStatic, wantsNonStatic, filter);
  3336. }
  3337. }
  3338. }
  3339. mAutoComplete->mInsertStartIdx = identifierNode->GetSrcStart();
  3340. mAutoComplete->mInsertEndIdx = identifierNode->GetSrcEnd();
  3341. AutocompleteAddTopLevelTypes(filter);
  3342. }
  3343. if (language == DbgLanguage_C)
  3344. {
  3345. // For C++ lambdas, captured a "this" is named "__this", so allow lookups into that
  3346. auto currentMethod = GetCurrentMethod();
  3347. if (currentMethod != NULL)
  3348. {
  3349. if (strstr(currentMethod->mName, "operator()") != NULL)
  3350. {
  3351. DbgTypedValue rootThisValue = GetThis();
  3352. if (rootThisValue)
  3353. {
  3354. DbgTypedValue thisValue = LookupField(identifierNode, rootThisValue, "__this");
  3355. if (thisValue)
  3356. {
  3357. if (findName == "this")
  3358. return thisValue;
  3359. auto fieldValue = LookupField(identifierNode, thisValue, findName);
  3360. if (fieldValue)
  3361. return fieldValue;
  3362. }
  3363. }
  3364. }
  3365. }
  3366. }
  3367. if (findName == "this")
  3368. return GetThis();
  3369. if (findName == "_")
  3370. {
  3371. if (mSubjectValue)
  3372. {
  3373. if (mSubjectValue.mSrcAddress != 0)
  3374. {
  3375. auto refreshVal = ReadTypedValue(identifierNode, mSubjectValue.mType, mSubjectValue.mSrcAddress, DbgAddrType_Target);
  3376. if (refreshVal)
  3377. mSubjectValue = refreshVal;
  3378. }
  3379. return mSubjectValue;
  3380. }
  3381. if (!mSubjectExpr.IsEmpty())
  3382. {
  3383. DwFormatInfo formatInfo;
  3384. formatInfo.mLanguage = language;
  3385. DbgEvaluationContext dbgEvaluationContext(mDebugger, mDbgModule, mSubjectExpr, &formatInfo);
  3386. mSubjectValue = dbgEvaluationContext.EvaluateInContext(mExplicitThis);
  3387. if (!mSubjectValue)
  3388. {
  3389. Fail("Failed to generate subject value", identifierNode);
  3390. }
  3391. if (mSubjectValue)
  3392. return mSubjectValue;
  3393. }
  3394. }
  3395. if (stackFrame != NULL)
  3396. {
  3397. if (mDebugTarget->GetValueByName(GetCurrentMethod(), findName, stackFrame, &valAddr, &valType, &addrType))
  3398. {
  3399. //BF_ASSERT(valType != NULL);
  3400. if (valType == NULL)
  3401. {
  3402. if (sizeof(addr_target) == 8)
  3403. valType = mDbgModule->GetPrimitiveType(DbgType_i64, DbgLanguage_C);
  3404. else
  3405. valType = mDbgModule->GetPrimitiveType(DbgType_i32, DbgLanguage_C);
  3406. }
  3407. if (valType != NULL)
  3408. {
  3409. if (mReferenceId != NULL)
  3410. *mReferenceId = findName;
  3411. //bool isLocal = !valIsAddr;
  3412. //if (valType->IsCompositeType())
  3413. //isLocal = false;
  3414. return ReadTypedValue(identifierNode, valType, valAddr, addrType);
  3415. }
  3416. }
  3417. }
  3418. bool isClosure = false;
  3419. if (language == DbgLanguage_Beef)
  3420. {
  3421. intptr valAddr;
  3422. DbgType* valType;
  3423. //bool valIsAddr = false;
  3424. if (mDebugTarget->GetValueByName(GetCurrentMethod(), "__closure", stackFrame, &valAddr, &valType, &addrType))
  3425. {
  3426. DbgTypedValue closureValue = ReadTypedValue(identifierNode, valType, valAddr, addrType);
  3427. if (closureValue)
  3428. {
  3429. SetAndRestoreValue<bool> prevIgnoreError(mIgnoreErrors, true);
  3430. DbgTypedValue fieldValue = LookupField(identifierNode, closureValue, findName);
  3431. if (fieldValue)
  3432. return fieldValue;
  3433. DbgTypedValue thisValue = LookupField(identifierNode, closureValue, "__this");
  3434. if (thisValue)
  3435. {
  3436. fieldValue = LookupField(identifierNode, thisValue, findName);
  3437. if (fieldValue)
  3438. return fieldValue;
  3439. }
  3440. }
  3441. }
  3442. }
  3443. /*if (mModule->mCurMethodState != NULL)
  3444. {
  3445. for (int localIdx = mModule->mCurMethodState->mLocals.size() - 1; localIdx >= 0; localIdx--)
  3446. {
  3447. auto& varDecl = mModule->mCurMethodState->mLocals[localIdx];
  3448. if (varDecl.mName == findName)
  3449. {
  3450. if (varDecl.mAddr != NULL)
  3451. {
  3452. return DbgTypedValue(varDecl.mAddr, varDecl.mUnresolvedType, true);
  3453. }
  3454. else
  3455. return DbgTypedValue(varDecl.mArgument, varDecl.mUnresolvedType, false);
  3456. return DbgTypedValue();
  3457. }
  3458. }
  3459. }*/
  3460. if (!isClosure)
  3461. {
  3462. // This uses an incorrect 'this' in the case of a closure
  3463. result = LookupField(identifierNode, DbgTypedValue(), findName);
  3464. if ((result) || (HasPropResult()))
  3465. return result;
  3466. }
  3467. result = GetRegister(findName);
  3468. if ((result) || (HasPropResult()))
  3469. {
  3470. return result;
  3471. }
  3472. mDbgModule->ParseGlobalsData();
  3473. for (auto compileUnit : mDbgModule->mCompileUnits)
  3474. {
  3475. if (mDbgCompileUnit == NULL)
  3476. continue;
  3477. if ((compileUnit->mLanguage != DbgLanguage_Unknown) && (compileUnit->mLanguage != mDbgCompileUnit->mLanguage))
  3478. continue;
  3479. result = DoLookupField(identifierNode, DbgTypedValue(), compileUnit->mGlobalType, findName, NULL, false);
  3480. if ((result) || (HasPropResult()))
  3481. return result;
  3482. }
  3483. auto currentMethod = GetCurrentMethod();
  3484. if ((currentMethod != NULL) && (currentMethod->mParentType == NULL) && (currentMethod->mHasQualifiedName))
  3485. {
  3486. currentMethod->mCompileUnit->mDbgModule->MapCompileUnitMethods(currentMethod->mCompileUnit);
  3487. }
  3488. if ((currentMethod != NULL) && (currentMethod->mParentType != NULL))
  3489. {
  3490. auto dbgType = currentMethod->mParentType;
  3491. if (dbgType->IsPointerOrRef())
  3492. dbgType = dbgType->mTypeParam;
  3493. auto curAlloc = &dbgType->mCompileUnit->mDbgModule->mAlloc;
  3494. result = DoLookupField(identifierNode, DbgTypedValue(), dbgType, findName, NULL, false);
  3495. if ((result) || (HasPropResult()))
  3496. return result;
  3497. GetNamespaceSearch();
  3498. for (auto usingNamespace : mNamespaceSearch)
  3499. {
  3500. usingNamespace = usingNamespace->GetPrimaryType();
  3501. result = DoLookupField(identifierNode, DbgTypedValue(), usingNamespace, findName, NULL, false);
  3502. if ((result) || (HasPropResult()))
  3503. return result;
  3504. for (auto checkNamespace : usingNamespace->mAlternates)
  3505. {
  3506. result = DoLookupField(identifierNode, DbgTypedValue(), checkNamespace, findName, NULL, false);
  3507. if ((result) || (HasPropResult()))
  3508. return result;
  3509. }
  3510. }
  3511. }
  3512. return DbgTypedValue();
  3513. }
  3514. DbgTypedValue DbgExprEvaluator::LookupIdentifier(BfAstNode* identifierNode, bool ignoreInitialError, bool* hadError)
  3515. {
  3516. if ((mStackSearch != NULL) && (mStackSearch->mIdentifier == NULL))
  3517. {
  3518. mStackSearch->mIdentifier = identifierNode;
  3519. mStackSearch->mStartingStackIdx = mCallStackIdx;
  3520. int skipCount = 0;
  3521. StringT<256> findStr;
  3522. for (int i = 0; i < mStackSearch->mSearchStr.mLength; i++)
  3523. {
  3524. char c = mStackSearch->mSearchStr[i];
  3525. if (c == '^')
  3526. {
  3527. skipCount = atoi(mStackSearch->mSearchStr.c_str() + i + 1);
  3528. break;
  3529. }
  3530. if (c == '.')
  3531. {
  3532. findStr += ':';
  3533. findStr += ':';
  3534. }
  3535. else
  3536. findStr += c;
  3537. }
  3538. while (true)
  3539. {
  3540. auto stackFrame = GetStackFrame();
  3541. bool matches = true;
  3542. if (mStackSearch->mSearchStr != "*")
  3543. {
  3544. mDebugger->UpdateCallStackMethod(mCallStackIdx);
  3545. if (stackFrame->mSubProgram != NULL)
  3546. {
  3547. int strLen = strlen(stackFrame->mSubProgram->mName);
  3548. if (strLen >= findStr.mLength)
  3549. {
  3550. if (strncmp(stackFrame->mSubProgram->mName + strLen - findStr.mLength, findStr.c_str(), findStr.mLength) == 0)
  3551. {
  3552. if (strLen > findStr.mLength)
  3553. {
  3554. char endC = stackFrame->mSubProgram->mName[strLen - findStr.mLength - 1];
  3555. if (endC != ':')
  3556. matches = false;
  3557. }
  3558. }
  3559. else
  3560. matches = false;
  3561. }
  3562. else
  3563. matches = false;
  3564. }
  3565. else
  3566. matches = false;
  3567. }
  3568. if (matches)
  3569. {
  3570. if (skipCount > 0)
  3571. {
  3572. skipCount--;
  3573. }
  3574. else
  3575. {
  3576. auto result = DoLookupIdentifier(identifierNode, ignoreInitialError, hadError);
  3577. if (result)
  3578. return result;
  3579. }
  3580. }
  3581. mCallStackIdx++;
  3582. if (mCallStackIdx >= mDebugger->mCallStack.mSize)
  3583. mDebugger->UpdateCallStack();
  3584. if (mCallStackIdx >= mDebugger->mCallStack.mSize)
  3585. return DbgTypedValue();
  3586. }
  3587. }
  3588. return DoLookupIdentifier(identifierNode, ignoreInitialError, hadError);
  3589. }
  3590. void DbgExprEvaluator::Visit(BfAssignmentExpression* assignExpr)
  3591. {
  3592. mHadSideEffects = true;
  3593. auto binaryOp = BfAssignOpToBinaryOp(assignExpr->mOp);
  3594. //auto ptr = mModule->GetOrCreateVarAddr(assignExpr->mLeft);
  3595. VisitChild(assignExpr->mLeft);
  3596. if ((!mResult) && (!HasPropResult()))
  3597. return;
  3598. if (HasPropResult())
  3599. {
  3600. if (mPropSet == NULL)
  3601. {
  3602. Fail("Property has no setter", mPropSrc);
  3603. return;
  3604. }
  3605. auto propSrc = mPropSrc;
  3606. auto propSet = mPropSet;
  3607. auto propTarget = mPropTarget;
  3608. auto indexerValues = mIndexerValues;
  3609. auto indexerExprValues = mIndexerExprValues;
  3610. mPropGet = NULL;
  3611. mPropSet = NULL;
  3612. mPropSrc = NULL;
  3613. mPropTarget = DbgTypedValue();
  3614. mIndexerValues.clear();
  3615. mIndexerExprValues.clear();
  3616. auto valueParam = propSet->mParams.back();
  3617. if (valueParam == NULL)
  3618. {
  3619. Fail("Invalid property setter", mPropSrc);
  3620. return;
  3621. }
  3622. DbgTypedValue convVal;
  3623. if (binaryOp != BfBinaryOp_None)
  3624. {
  3625. PerformBinaryOperation(assignExpr->mLeft, assignExpr->mRight, binaryOp, assignExpr->mOpToken, true);
  3626. if (!mResult)
  3627. return;
  3628. convVal = mResult;
  3629. }
  3630. else
  3631. {
  3632. convVal = CreateValueFromExpression(assignExpr->mRight, valueParam->mType);
  3633. }
  3634. if (!convVal)
  3635. return;
  3636. // SizedArray<DbgTypedValue, 4> argPushQueue;
  3637. // if (propSet->mHasThis)
  3638. // argPushQueue.push_back(propTarget);
  3639. // for (auto indexer : indexerValues)
  3640. // argPushQueue.push_back(indexer);
  3641. // argPushQueue.push_back(convVal);
  3642. // if (propSet->mParams.Size() == argPushQueue.size())
  3643. // {
  3644. // mResult = CreateCall(propSet, argPushQueue, false);
  3645. //
  3646. // }
  3647. indexerExprValues.push_back(assignExpr->mRight);
  3648. indexerValues.push_back(convVal);
  3649. mResult = CreateCall(propSrc, propTarget, propSet, false, indexerExprValues, indexerValues);
  3650. return;
  3651. }
  3652. GetResult();
  3653. auto ptr = mResult;
  3654. mResult = DbgTypedValue();
  3655. if (binaryOp != NULL)
  3656. {
  3657. PerformBinaryOperation(assignExpr->mLeft, assignExpr->mRight, binaryOp, assignExpr->mOpToken, true);
  3658. }
  3659. else
  3660. {
  3661. SetAndRestoreValue<DbgTypedValue*> prevReceiveValue(mReceivingValue, &ptr);
  3662. mResult = DbgTypedValue();
  3663. mResult = CreateValueFromExpression(assignExpr->mRight, ptr.mType, DbgEvalExprFlags_NoCast);
  3664. if (mReceivingValue == NULL)
  3665. {
  3666. // Receiving value used
  3667. mResult = ptr;
  3668. return;
  3669. }
  3670. }
  3671. if (!mResult)
  3672. return;
  3673. if ((ptr.mType->mTypeCode == DbgType_Ref) || (ptr.mType->mTypeCode == DbgType_RValueReference))
  3674. ptr.mType = ptr.mType->mTypeParam;
  3675. if ((mResult.mType->mTypeCode == DbgType_i32) && (mResult.mIsLiteral) && (ptr.mType->IsPointer()))
  3676. {
  3677. // Allow for literal pointer setting
  3678. mResult.mType = ptr.mType;
  3679. }
  3680. if ((mResult.mType->IsPointer()) && (mResult.mIsLiteral))
  3681. {
  3682. Fail("Cannot assign from literal value", assignExpr->mRight);
  3683. return;
  3684. }
  3685. mResult = Cast(assignExpr->mRight, mResult, ptr.mType, true);
  3686. if (!mResult)
  3687. return;
  3688. if ((mExpressionFlags & DwEvalExpressionFlag_AllowSideEffects) == 0)
  3689. {
  3690. mBlockedSideEffects = true;
  3691. return;
  3692. }
  3693. StoreValue(ptr, mResult, assignExpr->mLeft);
  3694. }
  3695. bool DbgExprEvaluator::StoreValue(DbgTypedValue& ptr, DbgTypedValue& value, BfAstNode* refNode)
  3696. {
  3697. if ((!HasPropResult()) && ((ptr.mSrcAddress == 0) || (ptr.mIsReadOnly)) && (ptr.mRegNum < 0))
  3698. {
  3699. Fail("Cannot assign to value", refNode);
  3700. return false;
  3701. }
  3702. if (ptr.mSrcAddress)
  3703. {
  3704. if (ptr.mType->mTypeCode == DbgType_Bitfield)
  3705. {
  3706. auto dbgBitfieldType = (DbgBitfieldType*)ptr.mType;
  3707. uint64 tempVal = 0;
  3708. mDebugger->ReadMemory(ptr.mSrcAddress, ptr.mType->GetByteCount(), &tempVal);
  3709. uint64 srcMask = ((uint64)1 << dbgBitfieldType->mLength) - 1;
  3710. uint64 destMask = srcMask << dbgBitfieldType->mPosition;
  3711. value.mUInt64 &= srcMask;
  3712. tempVal &= ~destMask;
  3713. tempVal |= value.mUInt64 << dbgBitfieldType->mPosition;
  3714. if (!mDebugger->WriteMemory(ptr.mSrcAddress, &tempVal, ptr.mType->GetByteCount()))
  3715. mPassInstance->Fail("Failed to write to memory");
  3716. if ((dbgBitfieldType->mTypeParam->IsSigned()) && ((value.mUInt64 & (1LL << (dbgBitfieldType->mLength - 1))) != 0))
  3717. {
  3718. // Sign extend
  3719. value.mUInt64 |= ~srcMask;
  3720. }
  3721. }
  3722. else
  3723. {
  3724. if (!mDebugger->WriteMemory(ptr.mSrcAddress, &value.mInt8, ptr.mType->GetByteCount()))
  3725. mPassInstance->Fail("Failed to write to memory");
  3726. }
  3727. }
  3728. else
  3729. {
  3730. String error;
  3731. if (!mDebugger->AssignToReg(mCallStackIdx, ptr, value, error))
  3732. mPassInstance->Fail(error);
  3733. }
  3734. return true;
  3735. }
  3736. bool DbgExprEvaluator::StoreValue(DbgTypedValue& ptr, BfExpression* expr)
  3737. {
  3738. auto receiveAddr = ptr.mSrcAddress;
  3739. if (receiveAddr == 0)
  3740. {
  3741. Fail("Unable to determine receiving address", expr);
  3742. return false;
  3743. }
  3744. SetAndRestoreValue<DbgTypedValue*> prevReceivingValue(mReceivingValue, &ptr);
  3745. auto wantType = ptr.mType->RemoveModifiers();
  3746. auto result = Resolve(expr, ptr.mType);
  3747. if (mReceivingValue == NULL)
  3748. return true; // Already written
  3749. if (!result)
  3750. return false;
  3751. return StoreValue(ptr, result, expr);;
  3752. }
  3753. void DbgExprEvaluator::Visit(BfParenthesizedExpression* parenExpr)
  3754. {
  3755. VisitChild(parenExpr->mExpression);
  3756. }
  3757. const char* DbgExprEvaluator::GetTypeName(DbgType* type)
  3758. {
  3759. if (type != NULL)
  3760. {
  3761. if (type->IsBfObjectPtr())
  3762. return "object";
  3763. if (type->IsPointer())
  3764. return "pointer";
  3765. }
  3766. return "value";
  3767. }
  3768. DbgTypedValue DbgExprEvaluator::GetResult()
  3769. {
  3770. if (!mResult)
  3771. {
  3772. if (HasPropResult())
  3773. {
  3774. if (mPropGet == NULL)
  3775. {
  3776. Fail("Property has no getter", mPropSrc);
  3777. }
  3778. else
  3779. {
  3780. // SizedArray<DbgTypedValue, 4> argPushQueue;
  3781. // auto curParam = mPropGet->mParams.mHead;
  3782. // if (mPropGet->mHasThis)
  3783. // {
  3784. // argPushQueue.push_back(mPropTarget);
  3785. // if (curParam != NULL)
  3786. // curParam = curParam->mNext;
  3787. // }
  3788. // bool failed = false;
  3789. // for (int indexerIdx = 0; indexerIdx < (int)mIndexerValues.size(); indexerIdx++)
  3790. // {
  3791. // auto val = mIndexerValues[indexerIdx];
  3792. // if (curParam != NULL)
  3793. // {
  3794. // val = Cast(mPropSrc, val, curParam->mType);
  3795. // if (!val)
  3796. // {
  3797. // failed = true;
  3798. // break;
  3799. // }
  3800. // }
  3801. // argPushQueue.push_back(val);
  3802. //
  3803. // if (curParam != NULL)
  3804. // curParam = curParam->mNext;
  3805. // }
  3806. // if (!failed)
  3807. // {
  3808. // if (mPropGet->mParams.Size() == argPushQueue.size())
  3809. // {
  3810. // mResult = CreateCall(mPropGet, argPushQueue, false);
  3811. // }
  3812. // else
  3813. // {
  3814. // Fail("Indexer parameter count mismatch", mPropSrc);
  3815. // }
  3816. // }
  3817. SetAndRestoreValue<DwEvalExpressionFlags> prevFlags(mExpressionFlags);
  3818. if ((mExpressionFlags & DwEvalExpressionFlag_AllowPropertyEval) != 0)
  3819. mExpressionFlags = (DwEvalExpressionFlags)(mExpressionFlags | DwEvalExpressionFlag_AllowCalls);
  3820. mResult = CreateCall(mPropSrc, mPropTarget, mPropGet, false, mIndexerExprValues, mIndexerValues);
  3821. }
  3822. }
  3823. }
  3824. if ((mResult) && (mResult.mType->IsConst()) && (GetLanguage() == DbgLanguage_Beef))
  3825. {
  3826. mResult.mIsReadOnly = true; // Pretend we don't really have the address
  3827. }
  3828. mPropGet = NULL;
  3829. mPropSet = NULL;
  3830. mPropSrc = NULL;
  3831. mIndexerValues.clear();
  3832. mIndexerExprValues.clear();
  3833. return mResult;
  3834. }
  3835. bool DbgExprEvaluator::HasPropResult()
  3836. {
  3837. return (mPropGet != NULL) || (mPropSet != NULL);
  3838. }
  3839. DbgLanguage DbgExprEvaluator::GetLanguage()
  3840. {
  3841. if (mLanguage != DbgLanguage_NotSet)
  3842. return mLanguage;
  3843. if ((mDbgCompileUnit != NULL) && (mDbgCompileUnit->mLanguage != DbgLanguage_Unknown))
  3844. return mDbgCompileUnit->mLanguage;
  3845. if (mExplicitThis)
  3846. return mExplicitThis.mType->mLanguage;
  3847. auto currentMethod = GetCurrentMethod();
  3848. if (currentMethod != NULL)
  3849. return currentMethod->GetLanguage();
  3850. return DbgLanguage_Beef; // Default to Beef
  3851. }
  3852. DbgFlavor DbgExprEvaluator::GetFlavor()
  3853. {
  3854. if (mDbgCompileUnit != NULL)
  3855. return mDbgCompileUnit->mDbgModule->mDbgFlavor;
  3856. if (mExplicitThis)
  3857. return mExplicitThis.mType->mCompileUnit->mDbgModule->mDbgFlavor;
  3858. return DbgFlavor_Unknown;
  3859. }
  3860. void DbgExprEvaluator::AutocompleteAddMethod(const char* methodName, const StringImpl& filter)
  3861. {
  3862. const char* atPos = strchr(methodName, '@');
  3863. if (atPos == NULL)
  3864. {
  3865. if ((strncmp(methodName, "get__", 5) == 0) ||
  3866. (strncmp(methodName, "set__", 5) == 0))
  3867. {
  3868. const char* propName = methodName + 5;
  3869. if (*propName != (char)0)
  3870. mAutoComplete->AddEntry(AutoCompleteEntry("property", propName), filter);
  3871. }
  3872. else if (strncmp(methodName, "__", 2) != 0)
  3873. mAutoComplete->AddEntry(AutoCompleteEntry("method", methodName), filter);
  3874. }
  3875. }
  3876. void DbgExprEvaluator::AutocompleteAddMembers(DbgType* dbgType, bool wantsStatic, bool wantsNonStatic, const StringImpl& filter, bool isCapture)
  3877. {
  3878. if (mStackSearch != NULL)
  3879. {
  3880. if (!mStackSearch->mAutocompleteSearchedTypes.Add(dbgType))
  3881. return;
  3882. }
  3883. DbgLanguage language = GetLanguage();
  3884. DbgFlavor flavor = GetFlavor();
  3885. if ((mDbgCompileUnit != NULL) && (dbgType->mLanguage != DbgLanguage_Unknown) && (dbgType->mLanguage != language))
  3886. return;
  3887. dbgType->PopulateType();
  3888. if (dbgType->mNeedsGlobalsPopulated)
  3889. mDbgModule->PopulateTypeGlobals(dbgType);
  3890. // Don't get primary type for namespace, causes mAlternates infinite loop
  3891. if (!dbgType->IsNamespace())
  3892. dbgType = dbgType->GetPrimaryType();
  3893. // false/false means just add subtypes
  3894. if ((wantsStatic) || (!wantsNonStatic))
  3895. {
  3896. auto subType = dbgType->mSubTypeList.mHead;
  3897. while (subType != NULL)
  3898. {
  3899. if (subType->mLanguage != language)
  3900. {
  3901. // Ignore
  3902. }
  3903. else if (subType->mTypeName == NULL)
  3904. {
  3905. AutocompleteAddMembers(subType, wantsStatic, wantsNonStatic, filter);
  3906. }
  3907. else
  3908. {
  3909. bool allowType = true;
  3910. for (const char* cPtr = subType->mTypeName; *cPtr != '\0'; cPtr++)
  3911. {
  3912. char c = *cPtr;
  3913. if ((c == '`') || (c == '[') || (c == '.') || (c == '$') || (c == '('))
  3914. allowType = false;
  3915. }
  3916. if ((allowType) && (subType->IsNamespace()))
  3917. {
  3918. // Is it a "using" declaration?
  3919. if ((!dbgType->IsRoot()) && (!dbgType->IsNamespace()))
  3920. allowType = false;
  3921. }
  3922. if ((!subType->IsAnonymous()) && (!subType->IsSizedArray()) && (allowType))
  3923. {
  3924. mDbgModule->TempRemoveTemplateStr(subType->mTypeName, subType->mTemplateNameIdx);
  3925. // We set the true mEntryType after the filter passes. This is because IsBfObject() is a "heavyweight" operation that we don't want to
  3926. // just run on ALL types immediately
  3927. AutoCompleteEntry* entry = mAutoComplete->AddEntry(AutoCompleteEntry("type", subType->mTypeName), filter);
  3928. if (entry != NULL)
  3929. {
  3930. if (subType->IsBfObject())
  3931. entry->mEntryType = "class";
  3932. else if (subType->IsNamespace())
  3933. entry->mEntryType = "namespace";
  3934. else
  3935. entry->mEntryType = "valuetype";
  3936. }
  3937. mDbgModule->ReplaceTemplateStr(subType->mTypeName, subType->mTemplateNameIdx);
  3938. }
  3939. else if (subType->IsGlobalsContainer())
  3940. {
  3941. if (subType->mPriority > DbgTypePriority_Normal)
  3942. AutocompleteAddMembers(subType, wantsStatic, wantsNonStatic, filter);
  3943. }
  3944. if ((subType->mTypeCode == DbgType_Enum) && (language == DbgLanguage_C))
  3945. {
  3946. AutocompleteAddMembers(subType, wantsStatic, wantsNonStatic, filter);
  3947. }
  3948. }
  3949. subType = subType->mNext;
  3950. }
  3951. if (dbgType->mTypeCode == DbgType_Namespace)
  3952. {
  3953. for (auto altType : dbgType->mAlternates)
  3954. {
  3955. AutocompleteAddMembers(altType, wantsStatic, wantsNonStatic, filter);
  3956. }
  3957. }
  3958. }
  3959. // In beef, all globals are stored inside global containers so we can skip the rest
  3960. bool skipMembers = (language == DbgLanguage_Beef) && (dbgType->mTypeCode == DbgType_Root);
  3961. if (skipMembers)
  3962. return;
  3963. for (auto member : dbgType->mMemberList)
  3964. {
  3965. if (((member->mIsStatic) && (wantsStatic)) ||
  3966. ((!member->mIsStatic) && (wantsNonStatic)))
  3967. {
  3968. const char* name = member->mName;
  3969. if (name != NULL)
  3970. {
  3971. if (member->mName[0] == '?')
  3972. continue;
  3973. mAutoComplete->AddEntry(AutoCompleteEntry(GetTypeName(member->mType), name), filter);
  3974. if ((isCapture) && (strcmp(member->mName, "__this") == 0))
  3975. {
  3976. mAutoComplete->AddEntry(AutoCompleteEntry(GetTypeName(member->mType), "this"), filter);
  3977. auto thisType = member->mType;
  3978. if (thisType->IsPointer())
  3979. thisType = thisType->mTypeParam;
  3980. thisType = thisType->RemoveModifiers();
  3981. AutocompleteAddMembers(thisType, wantsStatic, wantsNonStatic, filter);
  3982. }
  3983. }
  3984. else
  3985. {
  3986. AutocompleteAddMembers(member->mType, wantsStatic, wantsNonStatic, filter);
  3987. }
  3988. }
  3989. }
  3990. if ((dbgType->IsNamespace()) || (dbgType->IsRoot()))
  3991. {
  3992. // We only add these ones because we can be certain they are all static, otherwise we need the full
  3993. // method information which is in the compile units
  3994. for (auto methodNameEntry : dbgType->mMethodNameList)
  3995. {
  3996. const char* methodName = methodNameEntry->mName;
  3997. AutocompleteAddMethod(methodName, filter);
  3998. }
  3999. }
  4000. else
  4001. {
  4002. //TODO: Not needed since we added the declarations now, right?
  4003. //dbgType->EnsureMethodsMapped();
  4004. }
  4005. for (auto method : dbgType->mMethodList)
  4006. {
  4007. if (((!method->mHasThis) && (wantsStatic)) ||
  4008. ((method->mHasThis) && (wantsNonStatic)))
  4009. {
  4010. if ((method->mName != NULL) && (strcmp(method->mName, "this") != 0))
  4011. {
  4012. mDbgModule->FindTemplateStr(method->mName, method->mTemplateNameIdx);
  4013. if (method->mTemplateNameIdx == -1)
  4014. {
  4015. AutocompleteAddMethod(method->mName, filter);
  4016. }
  4017. }
  4018. }
  4019. }
  4020. /*if (!dbgType->mMethodNameList.IsEmpty())
  4021. {
  4022. BF_ASSERT(!dbgType->mMethodList.IsEmpty());
  4023. }*/
  4024. /*
  4025. for (auto methodNameEntry : dbgType->mMethodNameList)
  4026. {
  4027. const char* methodName = methodNameEntry->mName;
  4028. AutocompleteAddMethod(methodName, filter);
  4029. }*/
  4030. for (auto baseTypeEntry : dbgType->mBaseTypes)
  4031. {
  4032. AutocompleteAddMembers(baseTypeEntry->mBaseType, wantsStatic, wantsNonStatic, filter);
  4033. }
  4034. }
  4035. void DbgExprEvaluator::AutocompleteCheckMemberReference(BfAstNode* target, BfAstNode* dotToken, BfAstNode* memberName)
  4036. {
  4037. if ((IsAutoCompleteNode(dotToken)) || (IsAutoCompleteNode(memberName)))
  4038. {
  4039. mDbgModule->ParseGlobalsData();
  4040. bool isCType = dotToken->ToString() == "::";
  4041. String filter;
  4042. if (memberName != NULL)
  4043. {
  4044. filter = memberName->ToString();
  4045. mAutoComplete->mInsertStartIdx = memberName->GetSrcStart();
  4046. mAutoComplete->mInsertEndIdx = memberName->GetSrcEnd();
  4047. }
  4048. else
  4049. {
  4050. mAutoComplete->mInsertStartIdx = dotToken->GetSrcEnd();
  4051. mAutoComplete->mInsertEndIdx = dotToken->GetSrcEnd();
  4052. }
  4053. SetAndRestoreValue<bool> prevIgnoreError(mIgnoreErrors, true);
  4054. if (target == NULL)
  4055. {
  4056. mResult.mType = GetExpectingType();
  4057. if (mResult.mType != NULL)
  4058. mResult.mHasNoValue = true;
  4059. }
  4060. else if (auto typeRef = BfNodeDynCast<BfTypeReference>(target))
  4061. {
  4062. mResult.mType = ResolveTypeRef(typeRef);
  4063. mResult.mHasNoValue = true;
  4064. }
  4065. else
  4066. {
  4067. VisitChild(target);
  4068. GetResult();
  4069. }
  4070. if (mResult.mType != NULL)
  4071. {
  4072. mResult.mType = mResult.mType->RemoveModifiers();
  4073. auto dbgType = mResult.mType;
  4074. // if (dbgType->IsPrimitiveType())
  4075. // {
  4076. // //TODO: Boxed primitive structs
  4077. // }
  4078. //dbgType = dbgType->GetPrimaryType();
  4079. if ((dbgType != NULL) && (dbgType->IsPointerOrRef()))
  4080. {
  4081. dbgType = dbgType->mTypeParam;
  4082. dbgType = dbgType->RemoveModifiers();
  4083. }
  4084. //if (dbgType->mIsDeclaration)
  4085. dbgType = dbgType->GetPrimaryType();
  4086. if ((dbgType != NULL) /*&& ((dbgType->IsCompositeType()) || (dbgType->IsEnum()))*/)
  4087. {
  4088. bool wantsStatic = mResult.mHasNoValue;
  4089. bool wantsNonStatic = !mResult.mHasNoValue;
  4090. // C allows static lookups by non-static member reference
  4091. if (dbgType->GetLanguage() != DbgLanguage_Beef)
  4092. wantsStatic = true;
  4093. AutocompleteAddMembers(dbgType, wantsStatic, wantsNonStatic, filter);
  4094. if ((wantsStatic) && (dbgType->IsBfPayloadEnum()))
  4095. {
  4096. for (auto member : dbgType->mMemberList)
  4097. {
  4098. if ((member->mName[0] == '_') && (member->mName[1] >= '0') && (member->mName[1] <= '9'))
  4099. {
  4100. int val = atoi(member->mName + 1);
  4101. for (int i = 1; true; i++)
  4102. {
  4103. if (member->mName[i] == '_')
  4104. {
  4105. mAutoComplete->AddEntry(AutoCompleteEntry("method", member->mName + i + 1), filter);
  4106. break;
  4107. }
  4108. if (member->mName[i] == 0)
  4109. break;
  4110. }
  4111. }
  4112. }
  4113. }
  4114. }
  4115. //String prefixStr = dbgType->ToString();
  4116. //AutocompleteAddMembersFromNamespace(prefixStr, filter, isCType);
  4117. mResult = DbgTypedValue();
  4118. }
  4119. else
  4120. {
  4121. //return AutocompleteAddMembersFromNamespace(memberRefExpr->mTarget->ToString(), filter, isCType);
  4122. }
  4123. }
  4124. }
  4125. void DbgExprEvaluator::Visit(BfMemberReferenceExpression* memberRefExpr)
  4126. {
  4127. DbgTypedValue thisValue;
  4128. /*if (auto typeRef = BfNodeDynCast<DwTypeReference>(memberRefExpr->mTarget))
  4129. {
  4130. // Look up static field
  4131. //thisValue = DbgTypedValue(NULL, mModule->ResolveTypeRef(typeRef));
  4132. thisValue.mType = ResolveTypeRef(typeRef);
  4133. }*/
  4134. auto flavor = GetFlavor();
  4135. String findName;
  4136. BfAstNode* nameRefNode = memberRefExpr->mMemberName;
  4137. if (auto attrIdentifierExpr = BfNodeDynCast<BfAttributedIdentifierNode>(memberRefExpr->mMemberName))
  4138. {
  4139. nameRefNode = attrIdentifierExpr->mIdentifier;
  4140. if (nameRefNode != NULL)
  4141. findName = attrIdentifierExpr->mIdentifier->ToString();
  4142. }
  4143. else if (memberRefExpr->mMemberName != NULL)
  4144. findName = memberRefExpr->mMemberName->ToString();
  4145. AutocompleteCheckMemberReference(memberRefExpr->mTarget, memberRefExpr->mDotToken, nameRefNode);
  4146. //
  4147. {
  4148. SetAndRestoreValue<bool> prevIgnoreError(mIgnoreErrors, true);
  4149. mResult.mType = ResolveTypeRef(memberRefExpr);
  4150. if (mResult.mType != NULL)
  4151. {
  4152. mResult.mHasNoValue = true;
  4153. return;
  4154. }
  4155. }
  4156. if (memberRefExpr->mMemberName == NULL)
  4157. {
  4158. return;
  4159. }
  4160. if (memberRefExpr->mTarget == NULL)
  4161. {
  4162. auto expectingType = GetExpectingType();
  4163. if (expectingType != NULL)
  4164. {
  4165. DbgTypedValue expectingVal;
  4166. expectingVal.mType = expectingType;
  4167. mResult = LookupField(memberRefExpr->mMemberName, expectingVal, findName);
  4168. if ((mResult) || (HasPropResult()))
  4169. return;
  4170. }
  4171. }
  4172. {
  4173. SetAndRestoreValue<bool> prevIgnoreError(mIgnoreErrors, true);
  4174. if (memberRefExpr->mTarget == NULL)
  4175. thisValue.mType = mExpectingType;
  4176. else
  4177. thisValue.mType = ResolveTypeRef(memberRefExpr->mTarget, (BfAstNode**)&(memberRefExpr->mTarget));
  4178. if (thisValue.mType != NULL)
  4179. thisValue.mHasNoValue = true;
  4180. }
  4181. if (thisValue.mType == NULL)
  4182. {
  4183. if (auto exprTarget = BfNodeDynCast<BfExpression>(memberRefExpr->mTarget))
  4184. {
  4185. //thisValue = mModule->CreateValueFromExpression(exprTarget);
  4186. VisitChild(memberRefExpr->mTarget);
  4187. GetResult();
  4188. if (mResult.mType == NULL)
  4189. return;
  4190. mResult.mType = mResult.mType->RemoveModifiers();
  4191. thisValue = mResult;
  4192. }
  4193. else if (memberRefExpr->mTarget == NULL)
  4194. {
  4195. Fail("Identifier expected", memberRefExpr->mDotToken);
  4196. }
  4197. else
  4198. {
  4199. Fail("Unable to resolve target", memberRefExpr->mTarget);
  4200. }
  4201. }
  4202. /*else if (auto typeRef = BfNodeDynCast<BfTypeReference>(memberRefExpr->mTarget))
  4203. {
  4204. // Look up static field
  4205. thisValue.mType = ResolveTypeRef(typeRef);
  4206. }*/
  4207. if (thisValue.mSrcAddress == -1)
  4208. {
  4209. LookupSplatMember(memberRefExpr->mTarget, memberRefExpr, thisValue, findName);
  4210. }
  4211. else
  4212. mResult = LookupField(memberRefExpr->mMemberName, thisValue, findName);
  4213. /*if (mResult)
  4214. {
  4215. if (mReferenceId != NULL)
  4216. *mReferenceId = thisValue.mType->ToString() + "." + findName;
  4217. }*/
  4218. if ((!mResult) && (!HasPropResult()))
  4219. {
  4220. //String fullTokenString = memberRefExpr->ToString();
  4221. //mDbgModule->EnsureMethodsMapped(fullTokenString.c_str());
  4222. mResult = LookupField(memberRefExpr->mMemberName, thisValue, findName);
  4223. }
  4224. //TODO: Do type lookup?
  4225. if ((!mResult) && (!HasPropResult()))
  4226. {
  4227. if (thisValue.mHasNoValue)
  4228. {
  4229. for (auto altDwType : thisValue.mType->mAlternates)
  4230. {
  4231. auto altThisValue = thisValue;
  4232. altThisValue.mType = altDwType;
  4233. mResult = LookupField(memberRefExpr->mMemberName, altThisValue, findName);
  4234. if (mResult)
  4235. return;
  4236. }
  4237. }
  4238. Fail("Unable to find member", memberRefExpr->mMemberName);
  4239. }
  4240. }
  4241. DbgTypedValue DbgExprEvaluator::RemoveRef(DbgTypedValue typedValue)
  4242. {
  4243. bool hadRef = false;
  4244. typedValue.mType = typedValue.mType->RemoveModifiers(&hadRef);
  4245. if (hadRef)
  4246. typedValue.mSrcAddress = typedValue.mPtr;
  4247. return typedValue;
  4248. }
  4249. void DbgExprEvaluator::Visit(BfIndexerExpression* indexerExpr)
  4250. {
  4251. VisitChild(indexerExpr->mTarget);
  4252. GetResult();
  4253. if (!mResult)
  4254. return;
  4255. DbgTypedValue collection = RemoveRef(mResult);
  4256. bool indexerFailed = false;
  4257. mIndexerValues.clear();
  4258. mIndexerExprValues.clear();
  4259. SizedArray<BfExpression*, 2> indexerExprValues;
  4260. SizedArray<DbgTypedValue, 2> indexerValues;
  4261. for (auto indexExpr : indexerExpr->mArguments)
  4262. {
  4263. indexerExprValues.push_back(indexExpr);
  4264. VisitChild(indexExpr);
  4265. GetResult();
  4266. if (!mResult)
  4267. indexerFailed = true;
  4268. indexerValues.push_back(mResult);
  4269. mResult = DbgTypedValue();
  4270. }
  4271. if (indexerFailed)
  4272. {
  4273. mResult = DbgTypedValue();
  4274. return;
  4275. }
  4276. bool isBfArrayIndex = false;
  4277. if ((collection.mType->IsBfObjectPtr()) || (collection.mType->IsStruct()))
  4278. {
  4279. DbgType* bfType = collection.mType->mTypeParam;
  4280. if (bfType != NULL)
  4281. {
  4282. DbgType* baseType = bfType->GetBaseType();
  4283. if ((baseType != NULL) && (strcmp(baseType->mName, "System.Array") == 0))
  4284. {
  4285. isBfArrayIndex = true;
  4286. }
  4287. }
  4288. if (!isBfArrayIndex)
  4289. {
  4290. mIndexerExprValues = indexerExprValues;
  4291. mIndexerValues = indexerValues;
  4292. mResult = LookupField(indexerExpr->mTarget, collection, "");
  4293. if (HasPropResult())
  4294. {
  4295. // Only use this if we actually have the method. Otherwise fall through so we can try a debug visualizer or something
  4296. if ((mPropGet != NULL) && (mPropGet->mBlock.mLowPC != 0))
  4297. return;
  4298. }
  4299. // else
  4300. // {
  4301. // mResult = DbgTypedValue();
  4302. // Fail(StrFormat("Unable to index type '%s'", TypeToString(collection.mType).c_str()), indexerExpr->mOpenBracket);
  4303. // }
  4304. // return;
  4305. }
  4306. }
  4307. if (indexerValues.size() != 1)
  4308. {
  4309. Fail("Expected single index", indexerExpr->mOpenBracket);
  4310. return;
  4311. }
  4312. DbgTypedValue indexArgument = indexerValues[0];
  4313. indexArgument.mType = indexArgument.mType->RemoveModifiers();
  4314. if (!indexArgument.mType->IsInteger())
  4315. {
  4316. mResult = DbgTypedValue();
  4317. Fail("Expected integer index", indexerExpr->mArguments[0]);
  4318. return;
  4319. }
  4320. if (mReferenceId != NULL)
  4321. *mReferenceId += "[]";
  4322. if (isBfArrayIndex)
  4323. {
  4324. DbgType* bfType = collection.mType->mTypeParam;
  4325. bfType = bfType->GetPrimaryType();
  4326. DbgType* baseType = bfType->GetBaseType();
  4327. DbgVariable* lenVariable = baseType->mMemberList.mHead;
  4328. DbgVariable* typeVariable = bfType->mMemberList.mTail;
  4329. if ((lenVariable != NULL) && (typeVariable != NULL))
  4330. {
  4331. int len = mDebugger->ReadMemory<int>(collection.mPtr + lenVariable->mMemberOffset);
  4332. int idx = (int)indexArgument.GetInt64();
  4333. if ((idx < 0) || (idx >= len))
  4334. {
  4335. Fail("Index out of range", indexerExpr->mArguments[0]);
  4336. return;
  4337. }
  4338. auto result = ReadTypedValue(indexerExpr, typeVariable->mType, collection.mPtr + typeVariable->mMemberOffset + (idx * typeVariable->mType->GetStride()), DbgAddrType_Target);
  4339. if (mResult.mIsReadOnly)
  4340. result.mIsReadOnly = true;
  4341. mResult = result;
  4342. return;
  4343. }
  4344. }
  4345. SetAndRestoreValue<String*> prevReferenceId(mReferenceId, NULL);
  4346. Array<String> dbgVisWildcardCaptures;
  4347. auto debugVis = mDebugger->FindVisualizerForType(collection.mType, &dbgVisWildcardCaptures);
  4348. if (debugVis != NULL)
  4349. {
  4350. if ((debugVis->mCollectionType == DebugVisualizerEntry::CollectionType_Array) && (debugVis->mLowerDimSizes.size() == 0))
  4351. {
  4352. auto debugVisualizers = mDebugger->mDebugManager->mDebugVisualizers;
  4353. DbgTypedValue sizeValue = mDebugger->EvaluateInContext(mDbgCompileUnit, collection, debugVisualizers->DoStringReplace(debugVis->mSize, dbgVisWildcardCaptures));
  4354. Array<int> lowerDimSizes;
  4355. if (sizeValue)
  4356. {
  4357. int len = (int)sizeValue.GetInt64();
  4358. int idx = (int)indexArgument.GetInt64();
  4359. if ((idx < 0) || (idx >= len))
  4360. {
  4361. Fail("Index out of range", indexerExpr->mArguments[0]);
  4362. return;
  4363. }
  4364. addr_target dataPtr = (collection.mType->IsPointer()) ? collection.mPtr : collection.mSrcAddress;
  4365. String ptrUseDataTypeStr = collection.mType->ToStringRaw();
  4366. String ptrUseDataStr = StrFormat("(%s)", ptrUseDataTypeStr.c_str()) + EncodeDataPtr(dataPtr, true);
  4367. //String evalStr = "(" + debugVisualizers->DoStringReplace(debugVis->mValuePointer, dbgVisWildcardCaptures) + StrFormat("[%d]), this=", idx);
  4368. String evalStr = "*(" + debugVisualizers->DoStringReplace(debugVis->mValuePointer, dbgVisWildcardCaptures) + StrFormat(" + %d), this=", idx) + ptrUseDataStr;
  4369. evalStr += ptrUseDataStr;
  4370. auto result = mDebugger->EvaluateInContext(mDbgCompileUnit, collection, evalStr);
  4371. if (mResult.mIsReadOnly)
  4372. result.mIsReadOnly = true;
  4373. mResult = result;
  4374. if (mResult)
  4375. return;
  4376. }
  4377. }
  4378. }
  4379. addr_target target = collection.mPtr;
  4380. if (collection.mType->mTypeCode == DbgType_SizedArray)
  4381. target = collection.mSrcAddress;
  4382. if ((!collection.mType->IsPointer()) && (collection.mType->mTypeCode != DbgType_SizedArray))
  4383. {
  4384. mResult = DbgTypedValue();
  4385. //Fail("Expected pointer type", indexerExpr->mTarget);
  4386. Fail(StrFormat("Unable to index type '%s'", TypeToString(collection.mType).c_str()), indexerExpr->mOpenBracket);
  4387. return;
  4388. }
  4389. if (collection.mType->mTypeCode == DbgType_SizedArray)
  4390. {
  4391. int innerSize = collection.mType->mTypeParam->GetStride();
  4392. int len = 0;
  4393. if (innerSize > 0)
  4394. len = collection.mType->GetStride() / innerSize;
  4395. int idx = (int)indexArgument.GetInt64();
  4396. if ((idx < 0) || (idx >= len))
  4397. {
  4398. Fail("Index out of range", indexerExpr->mArguments[0]);
  4399. return;
  4400. }
  4401. }
  4402. if ((collection.mType->IsBfObjectPtr()) || (collection.mType->IsStruct()))
  4403. {
  4404. // This should have been handled by some other cases
  4405. mResult = DbgTypedValue();
  4406. Fail(StrFormat("Unable to index type '%s'", TypeToString(collection.mType).c_str()), indexerExpr->mOpenBracket);
  4407. }
  4408. auto memberType = collection.mType->mTypeParam;
  4409. auto result = ReadTypedValue(indexerExpr, memberType, target + indexArgument.GetInt64() * memberType->GetStride(), DbgAddrType_Target);
  4410. if (mResult.mIsReadOnly)
  4411. result.mIsReadOnly = true;
  4412. mResult = result;
  4413. }
  4414. void DbgExprEvaluator::Visit(BfThisExpression* thisExpr)
  4415. {
  4416. if (mExplicitThis)
  4417. {
  4418. if (mExplicitThisExpr != NULL)
  4419. mDeferredInsertExplicitThisVector.push_back(NodeReplaceRecord(thisExpr, mCurChildRef));
  4420. mResult = mExplicitThis;
  4421. /*if (mReferenceId != NULL)
  4422. {
  4423. auto checkType = mExplicitThis.mType;
  4424. if (checkType->IsPointer())
  4425. checkType = checkType->mTypeParam;
  4426. *mReferenceId = checkType->ToString(true);
  4427. }*/
  4428. return;
  4429. }
  4430. bool hadError;
  4431. mResult = LookupIdentifier(thisExpr, false, &hadError);
  4432. if (!mResult)
  4433. {
  4434. if (GetCurrentMethod() != NULL)
  4435. Fail("Static methods don't have 'this'", thisExpr);
  4436. else
  4437. Fail("Execution must be paused to retrieve 'this'", thisExpr);
  4438. }
  4439. }
  4440. void DbgExprEvaluator::Visit(BfIdentifierNode* identifierNode)
  4441. {
  4442. //BfLogDbgExpr("Visit BfIdentifierNode %s\n", identifierNode->ToString().c_str());
  4443. mResult = LookupIdentifier(identifierNode, false, NULL);
  4444. if (!mResult)
  4445. {
  4446. //??
  4447. //mDbgModule->EnsureMethodsMapped(identifierNode->ToString().c_str());
  4448. //mResult = LookupIdentifier(identifierNode, false, NULL);
  4449. }
  4450. if ((mResult) || (HasPropResult()))
  4451. return;
  4452. {
  4453. SetAndRestoreValue<bool> prevIgnoreError(mIgnoreErrors, true);
  4454. mResult.mType = ResolveTypeRef(identifierNode);
  4455. if (mResult.mType != NULL)
  4456. {
  4457. mResult.mHasNoValue = true;
  4458. return;
  4459. }
  4460. }
  4461. Fail("Identifier not found", identifierNode);
  4462. }
  4463. void DbgExprEvaluator::Visit(BfAttributedIdentifierNode* node)
  4464. {
  4465. VisitChild(node->mIdentifier);
  4466. }
  4467. void DbgExprEvaluator::Visit(BfMixinExpression* mixinExpr)
  4468. {
  4469. mResult = LookupIdentifier(mixinExpr, false, NULL);
  4470. if (mResult)
  4471. return;
  4472. Fail("Identifier not found", mixinExpr);
  4473. }
  4474. void DbgExprEvaluator::LookupSplatMember(const DbgTypedValue& target, const StringImpl& fieldName)
  4475. {
  4476. BF_ASSERT(target.mSrcAddress == -1);
  4477. DbgVariable* dbgVariable = (DbgVariable*)target.mVariable;
  4478. if (dbgVariable == NULL)
  4479. return;
  4480. auto wantType = target.mType->RemoveModifiers();
  4481. auto checkType = dbgVariable->mType->RemoveModifiers();
  4482. // Use real name, in case of aliases
  4483. String findName = target.mVariable->mName;
  4484. bool foundWantType = false;
  4485. /*if (checkType != wantType)
  4486. {
  4487. checkType = valType;
  4488. foundWantType = false;
  4489. if (checkType->IsBfPayloadEnum())
  4490. {
  4491. if (wasCast)
  4492. {
  4493. findName += "$u";
  4494. checkType = wantType;
  4495. foundWantType = true;
  4496. }
  4497. }
  4498. }*/
  4499. bool found = false;
  4500. while (checkType != NULL)
  4501. {
  4502. checkType = checkType->GetPrimaryType();
  4503. if ((!foundWantType) && (checkType->Equals(wantType)))
  4504. foundWantType = true;
  4505. if (foundWantType)
  4506. {
  4507. for (auto member : checkType->mMemberList)
  4508. {
  4509. if (member->mName == fieldName)
  4510. {
  4511. found = true;
  4512. break;
  4513. }
  4514. }
  4515. }
  4516. if (found)
  4517. break;
  4518. checkType = checkType->GetBaseType();
  4519. findName += "$b";
  4520. }
  4521. if (found)
  4522. {
  4523. findName = "$" + findName + "$m$" + fieldName;
  4524. CPUStackFrame* stackFrame = GetStackFrame();
  4525. intptr valAddr;
  4526. DbgType* valType;
  4527. DbgAddrType addrType = DbgAddrType_Value;
  4528. if (mDebugTarget->GetValueByName(GetCurrentMethod(), findName, stackFrame, &valAddr, &valType, &addrType))
  4529. {
  4530. BF_ASSERT(valType != NULL);
  4531. if (valType != NULL)
  4532. {
  4533. if (mReferenceId != NULL)
  4534. *mReferenceId = findName;
  4535. mResult = ReadTypedValue(NULL, valType, valAddr, addrType);
  4536. return;
  4537. }
  4538. }
  4539. }
  4540. }
  4541. void DbgExprEvaluator::LookupSplatMember(BfAstNode* targetNode, BfAstNode* lookupNode, const DbgTypedValue& target, const StringImpl& fieldName, String* outFindName, bool* outIsConst, StringImpl* forceName)
  4542. {
  4543. /*DbgVariable* dbgVariable = (DbgVariable*)target.mVariable;
  4544. if (dbgVariable != NULL)
  4545. return LookupSplatMember(target, fieldName);*/
  4546. auto curMethod = GetCurrentMethod();
  4547. while (auto parenNode = BfNodeDynCast<BfParenthesizedExpression>(lookupNode))
  4548. lookupNode = parenNode->mExpression;
  4549. SplatLookupEntry* splatLookupEntry = NULL;
  4550. if (lookupNode != NULL)
  4551. {
  4552. if (mSplatLookupMap.TryAdd(lookupNode, NULL, &splatLookupEntry))
  4553. {
  4554. //
  4555. }
  4556. else if (forceName == NULL)
  4557. {
  4558. if (outFindName != NULL)
  4559. *outFindName = splatLookupEntry->mFindName;
  4560. if (outIsConst != NULL)
  4561. *outIsConst = splatLookupEntry->mIsConst;
  4562. mResult = splatLookupEntry->mResult;
  4563. return;
  4564. }
  4565. }
  4566. String findName;
  4567. bool wasCast = false;
  4568. mResult = DbgTypedValue();
  4569. BfAstNode* checkNode = targetNode;
  4570. BfAstNode* parentNode = NULL;
  4571. while (true)
  4572. {
  4573. if (checkNode == NULL)
  4574. return;
  4575. if (auto qualifiedNameNode = BfNodeDynCast<BfQualifiedNameNode>(checkNode))
  4576. {
  4577. parentNode = qualifiedNameNode->mLeft;
  4578. findName = qualifiedNameNode->mRight->ToString();
  4579. break;
  4580. }
  4581. else if (auto memberRefExpr = BfNodeDynCast<BfMemberReferenceExpression>(checkNode))
  4582. {
  4583. parentNode = memberRefExpr->mTarget;
  4584. findName = memberRefExpr->mMemberName->ToString();
  4585. break;
  4586. }
  4587. else if (auto identifier = BfNodeDynCast<BfIdentifierNode>(checkNode))
  4588. {
  4589. findName = identifier->ToString();
  4590. break;
  4591. }
  4592. else if (auto thisExpr = BfNodeDynCast<BfThisExpression>(checkNode))
  4593. {
  4594. findName = thisExpr->ToString();
  4595. break;
  4596. }
  4597. else if (auto castExpr = BfNodeDynCast<BfCastExpression>(checkNode))
  4598. {
  4599. wasCast = true;
  4600. checkNode = castExpr->mExpression;
  4601. }
  4602. else if (auto parenExpr = BfNodeDynCast<BfParenthesizedExpression>(checkNode))
  4603. {
  4604. checkNode = parenExpr->mExpression;
  4605. }
  4606. else
  4607. return;
  4608. }
  4609. if (forceName != NULL)
  4610. findName = *forceName;
  4611. CPUStackFrame* stackFrame = GetStackFrame();
  4612. intptr valAddr;
  4613. DbgType* valType = NULL;
  4614. DbgAddrType addrType = DbgAddrType_Value;
  4615. bool foundWantType = true;
  4616. DbgType* wantType = target.mType;
  4617. auto checkType = target.mType;
  4618. checkType = checkType->RemoveModifiers();
  4619. bool valWasConst = false;
  4620. bool foundParent = false;
  4621. if (target.mSrcAddress == -1)
  4622. {
  4623. if (parentNode != NULL)
  4624. {
  4625. DbgTypedValue origTarget;
  4626. origTarget.mSrcAddress = -1;
  4627. origTarget.mType = target.mVariable->mType;
  4628. origTarget.mVariable = target.mVariable;
  4629. bool parentIsConst = false;
  4630. String parentFindName;
  4631. LookupSplatMember(parentNode, targetNode, origTarget, findName, &parentFindName, &parentIsConst);
  4632. if (!parentFindName.IsEmpty())
  4633. {
  4634. foundParent = true;
  4635. findName = parentFindName;
  4636. valType = mResult.mType;
  4637. valWasConst = parentIsConst;
  4638. }
  4639. }
  4640. }
  4641. if (!foundParent)
  4642. {
  4643. if (!mDebugTarget->GetValueByName(curMethod, findName, stackFrame, &valAddr, &valType, &addrType))
  4644. return;
  4645. if (addrType == DbgAddrType_Alias)
  4646. {
  4647. findName = (const char*)valAddr;
  4648. if (!mDebugTarget->GetValueByName(curMethod, findName, stackFrame, &valAddr, &valType, &addrType))
  4649. {
  4650. if (curMethod->mInlineeInfo != NULL)
  4651. {
  4652. // Look outside to inline
  4653. SetAndRestoreValue<int> prevStackIdx(mCallStackIdx, mCallStackIdx + 1);
  4654. LookupSplatMember(targetNode, lookupNode, target, fieldName, outFindName, outIsConst, &findName);
  4655. return;
  4656. }
  4657. return;
  4658. }
  4659. }
  4660. if (addrType == DbgAddrType_LocalSplat)
  4661. {
  4662. DbgVariable* dbgVariable = (DbgVariable*)valAddr;
  4663. // Use real name, in case of aliases
  4664. findName = dbgVariable->mName;
  4665. }
  4666. }
  4667. if ((wasCast) && (valType != NULL))
  4668. {
  4669. checkType = valType->RemoveModifiers();
  4670. foundWantType = false;
  4671. if (checkType->IsBfPayloadEnum())
  4672. {
  4673. if (wasCast)
  4674. {
  4675. findName += "$u";
  4676. checkType = wantType;
  4677. foundWantType = true;
  4678. }
  4679. }
  4680. }
  4681. mResult = DbgTypedValue();
  4682. if (valType != NULL)
  4683. valWasConst |= valType->IsConst();
  4684. DbgType* memberType = NULL;
  4685. bool found = false;
  4686. bool wasUnion = false;
  4687. while (checkType != NULL)
  4688. {
  4689. checkType = checkType->GetPrimaryType();
  4690. if ((!foundWantType) && (checkType->Equals(wantType)))
  4691. foundWantType = true;
  4692. if (foundWantType)
  4693. {
  4694. for (auto member : checkType->mMemberList)
  4695. {
  4696. if (member->mName == fieldName)
  4697. {
  4698. wasUnion = checkType->IsBfUnion();
  4699. memberType = member->mType;
  4700. found = true;
  4701. break;
  4702. }
  4703. }
  4704. }
  4705. if (found)
  4706. break;
  4707. checkType = checkType->GetBaseType();
  4708. findName += "$b";
  4709. }
  4710. if (found)
  4711. {
  4712. bool wantConst = ((valWasConst) && (!memberType->IsConst()) && (!memberType->IsRef()));
  4713. if (!findName.StartsWith("$"))
  4714. findName = "$" + findName;
  4715. if (wasUnion)
  4716. findName += "$u";
  4717. else
  4718. findName += "$m$" + fieldName;
  4719. if (outFindName != NULL)
  4720. *outFindName = findName;
  4721. if (outIsConst != NULL)
  4722. *outIsConst = wantConst;
  4723. if (mDebugTarget->GetValueByName(curMethod, findName, stackFrame, &valAddr, &valType, &addrType))
  4724. {
  4725. BF_ASSERT(valType != NULL);
  4726. if (valType != NULL)
  4727. {
  4728. if (mReferenceId != NULL)
  4729. *mReferenceId = findName;
  4730. /*if ((valType->IsConst()) && (!memberType->IsConst()))
  4731. {
  4732. // Set readonly if the original value was const
  4733. memberType = mDbgModule->GetConstType(valType);
  4734. }*/
  4735. mResult = ReadTypedValue(targetNode, memberType, valAddr, addrType);
  4736. if (wantConst)
  4737. {
  4738. // Set readonly if the original value was const
  4739. mResult.mIsReadOnly = true;
  4740. }
  4741. }
  4742. }
  4743. else
  4744. {
  4745. if (target.mSrcAddress == -1)
  4746. {
  4747. // if (curMethod->mInlineeInfo != NULL)
  4748. // {
  4749. // // Look outside to inline
  4750. // SetAndRestoreValue<int> prevStackIdx(mCallStackIdx, mCallStackIdx + 1);
  4751. // LookupSplatMember(targetNode, lookupNode, target, fieldName, outFindName, outIsConst, true);
  4752. // return;
  4753. // }
  4754. if (!memberType->IsStruct())
  4755. Fail("Failed to lookup splat member", (lookupNode != NULL) ? lookupNode : targetNode);
  4756. if ((target.mVariable == NULL) && (target.mType->GetByteCount() != 0))
  4757. Fail("Splat variable not found", (lookupNode != NULL) ? lookupNode : targetNode);
  4758. //BF_ASSERT((target.mVariable != NULL) || (target.mType->GetByteCount() == 0));
  4759. mResult = target;
  4760. mResult.mType = memberType;
  4761. }
  4762. }
  4763. if (splatLookupEntry != NULL)
  4764. {
  4765. splatLookupEntry->mFindName = findName;
  4766. splatLookupEntry->mIsConst = wantConst;
  4767. splatLookupEntry->mResult = mResult;
  4768. }
  4769. }
  4770. }
  4771. void DbgExprEvaluator::LookupQualifiedName(BfQualifiedNameNode* nameNode, bool ignoreInitialError, bool* hadError)
  4772. {
  4773. String fieldName = nameNode->mRight->ToString();
  4774. mResult = LookupIdentifier(nameNode->mLeft, ignoreInitialError, hadError);
  4775. mResult = GetResult();
  4776. if (!mResult)
  4777. {
  4778. if (!ignoreInitialError)
  4779. Fail("Identifier not found", nameNode->mLeft);
  4780. return;
  4781. }
  4782. if (!mResult)
  4783. return;
  4784. /*if (!mResult.mType->IsTypeInstance())
  4785. {
  4786. Fail("Type has no fields", nameNode->mLeft);
  4787. return;
  4788. }*/
  4789. if (mResult.mSrcAddress == -1)
  4790. {
  4791. auto target = mResult;
  4792. mResult = DbgTypedValue();
  4793. LookupSplatMember(nameNode->mLeft, nameNode, target, fieldName);
  4794. }
  4795. else
  4796. {
  4797. mResult = LookupField(nameNode, mResult, fieldName);
  4798. if (mPropSrc != NULL)
  4799. {
  4800. if (nameNode->mLeft->ToString() == "base")
  4801. {
  4802. //mPropDefBypassVirtual = true;
  4803. }
  4804. }
  4805. }
  4806. if ((mResult) || (mPropSrc != NULL))
  4807. return;
  4808. if (hadError != NULL)
  4809. *hadError = true;
  4810. Fail("Unable to find member", nameNode->mRight);
  4811. }
  4812. DbgType* DbgExprEvaluator::FindSubtype(DbgType* type, const StringImpl& name)
  4813. {
  4814. for (auto subType : type->mSubTypeList)
  4815. {
  4816. if ((subType->mTypeName != NULL) && (strcmp(subType->mTypeName, name.c_str()) == 0))
  4817. return subType;
  4818. }
  4819. for (auto baseType : type->mBaseTypes)
  4820. {
  4821. auto subType = FindSubtype(baseType->mBaseType->GetPrimaryType(), name);
  4822. if (subType != NULL)
  4823. return subType;
  4824. }
  4825. return NULL;
  4826. }
  4827. void DbgExprEvaluator::LookupQualifiedStaticField(BfQualifiedNameNode* nameNode, bool ignoreIdentifierNotFoundError)
  4828. {
  4829. // Lookup left side as a type
  4830. {
  4831. DbgType* type;
  4832. {
  4833. SetAndRestoreValue<bool> prevIgnoreErro(mIgnoreErrors, true);
  4834. type = ResolveTypeRef(nameNode->mLeft);
  4835. }
  4836. if (type != NULL)
  4837. {
  4838. DbgTypedValue lookupType;
  4839. /*if (type->IsPrimitiveType())
  4840. lookupType.mType = mModule->GetPrimitiveStructType(type));
  4841. else*/
  4842. lookupType.mType = type;
  4843. lookupType.mHasNoValue = true;
  4844. mResult = LookupField(nameNode->mRight, lookupType, nameNode->mRight->ToString());
  4845. if ((mResult) || (mPropSrc != NULL))
  4846. return;
  4847. DbgType* fullType = NULL;
  4848. //
  4849. {
  4850. SetAndRestoreValue<bool> prevIgnoreError(mIgnoreErrors, true);
  4851. fullType = ResolveTypeRef(nameNode);
  4852. if ((fullType == NULL) && (!type->IsNamespace()))
  4853. {
  4854. String subName = nameNode->mRight->ToString();
  4855. fullType = FindSubtype(type, subName);
  4856. }
  4857. }
  4858. if (fullType != NULL)
  4859. {
  4860. mResult.mType = fullType;
  4861. mResult.mHasNoValue = true;
  4862. return;
  4863. }
  4864. Fail("Field not found", nameNode->mRight);
  4865. return;
  4866. }
  4867. }
  4868. String fieldName = nameNode->mRight->ToString();
  4869. if (auto qualifiedLeftName = BfNodeDynCast<BfQualifiedNameNode>(nameNode->mLeft))
  4870. LookupQualifiedStaticField(qualifiedLeftName);
  4871. else
  4872. VisitChild(nameNode->mLeft);
  4873. GetResult();
  4874. if (!mResult)
  4875. {
  4876. Fail("Identifier not found", nameNode->mLeft);
  4877. return;
  4878. }
  4879. if (!mResult)
  4880. return;
  4881. auto checkType = mResult.mType->RemoveModifiers();
  4882. if (checkType->IsPointer())
  4883. checkType = checkType->mTypeParam;
  4884. if ((checkType == NULL) || (!checkType->IsCompositeType()))
  4885. {
  4886. Fail("Type has no fields", nameNode->mLeft);
  4887. return;
  4888. }
  4889. mResult = LookupField(nameNode, mResult, fieldName);
  4890. if ((mResult) || (mPropSrc != NULL))
  4891. return;
  4892. Fail("Unable to find member", nameNode->mRight);
  4893. }
  4894. bool DbgExprEvaluator::EnsureRunning(BfAstNode* astNode)
  4895. {
  4896. if (mDebugger->mIsRunning)
  4897. return true;
  4898. Fail("Target is not running", astNode);
  4899. return false;
  4900. }
  4901. void DbgExprEvaluator::Visit(BfQualifiedNameNode* nameNode)
  4902. {
  4903. AutocompleteCheckMemberReference(nameNode->mLeft, nameNode->mDot, nameNode->mRight);
  4904. bool hadError = false;
  4905. LookupQualifiedName(nameNode, true, &hadError);
  4906. if ((mResult) || (mPropSrc != NULL))
  4907. return;
  4908. if (hadError)
  4909. return;
  4910. LookupQualifiedStaticField(nameNode);
  4911. }
  4912. void DbgExprEvaluator::Visit(BfDefaultExpression* defaultExpr)
  4913. {
  4914. mIsComplexExpression = true;
  4915. /*auto type = mModule->ResolveTypeRef(defaultExpr->mTypeRef);
  4916. if (!type)
  4917. return;
  4918. mResult = DbgTypedValue(mModule->GetDefaultValue(type), type);*/
  4919. }
  4920. void DbgExprEvaluator::Visit(BfLiteralExpression* literalExpr)
  4921. {
  4922. mIsComplexExpression = true;
  4923. mResult.mIsLiteral = true;
  4924. auto language = GetLanguage();
  4925. switch (literalExpr->mValue.mTypeCode)
  4926. {
  4927. case BfTypeCode_NullPtr:
  4928. {
  4929. mResult.mPtr = 0;
  4930. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Null, GetLanguage());
  4931. }
  4932. break;
  4933. case BfTypeCode_CharPtr:
  4934. mResult = GetString(*literalExpr->mValue.mString);
  4935. break;
  4936. case BfTypeCode_Boolean:
  4937. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  4938. mResult.mBool = literalExpr->mValue.mBool;
  4939. break;
  4940. case BfTypeCode_Char8:
  4941. mResult.mType = mDbgModule->GetPrimitiveType((language == DbgLanguage_Beef) ? DbgType_UChar : DbgType_SChar, language);
  4942. mResult.mInt8 = literalExpr->mValue.mInt8;
  4943. break;
  4944. case BfTypeCode_Char16:
  4945. mResult.mType = mDbgModule->GetPrimitiveType((language == DbgLanguage_Beef) ? DbgType_UChar16 : DbgType_SChar16, language);
  4946. mResult.mInt16 = literalExpr->mValue.mInt16;
  4947. break;
  4948. case BfTypeCode_Char32:
  4949. mResult.mType = mDbgModule->GetPrimitiveType((language == DbgLanguage_Beef) ? DbgType_UChar32 : DbgType_SChar32, language);
  4950. mResult.mInt32 = literalExpr->mValue.mInt32;
  4951. break;
  4952. case BfTypeCode_Int8:
  4953. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_i8, GetLanguage());
  4954. mResult.mUInt8 = literalExpr->mValue.mUInt8;
  4955. break;
  4956. case BfTypeCode_UInt8:
  4957. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_u8, GetLanguage());
  4958. mResult.mUInt8 = literalExpr->mValue.mUInt8;
  4959. break;
  4960. case BfTypeCode_Int16:
  4961. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_i16, GetLanguage());
  4962. mResult.mInt16 = literalExpr->mValue.mInt16;
  4963. break;
  4964. case BfTypeCode_UInt16:
  4965. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_u16, GetLanguage());
  4966. mResult.mUInt16 = literalExpr->mValue.mUInt16;
  4967. break;
  4968. case BfTypeCode_Int32:
  4969. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_i32, GetLanguage());
  4970. mResult.mInt32 = literalExpr->mValue.mInt32;
  4971. break;
  4972. case BfTypeCode_UInt32:
  4973. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_u32, GetLanguage());
  4974. mResult.mUInt32 = literalExpr->mValue.mUInt32;
  4975. break;
  4976. case BfTypeCode_Int64:
  4977. case BfTypeCode_IntUnknown:
  4978. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_i64, GetLanguage());
  4979. mResult.mInt64 = literalExpr->mValue.mInt64;
  4980. break;
  4981. case BfTypeCode_UInt64:
  4982. case BfTypeCode_UIntUnknown:
  4983. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_u64, GetLanguage());
  4984. mResult.mUInt64 = literalExpr->mValue.mUInt64;
  4985. break;
  4986. case BfTypeCode_IntPtr:
  4987. if (sizeof(addr_target) == 8)
  4988. {
  4989. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_i64, GetLanguage());
  4990. mResult.mInt64 = literalExpr->mValue.mInt64;
  4991. }
  4992. else
  4993. {
  4994. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_i32, GetLanguage());
  4995. mResult.mInt32 = literalExpr->mValue.mInt32;
  4996. }
  4997. break;
  4998. case BfTypeCode_UIntPtr:
  4999. if (sizeof(addr_target) == 8)
  5000. {
  5001. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_u64, GetLanguage());
  5002. mResult.mUInt64 = literalExpr->mValue.mUInt64;
  5003. }
  5004. else
  5005. {
  5006. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_u32, GetLanguage());
  5007. mResult.mUInt32 = literalExpr->mValue.mUInt32;
  5008. }
  5009. break;
  5010. case BfTypeCode_Float:
  5011. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Single, GetLanguage());
  5012. mResult.mSingle = literalExpr->mValue.mSingle;
  5013. break;
  5014. case BfTypeCode_Double:
  5015. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Double, GetLanguage());
  5016. mResult.mDouble = literalExpr->mValue.mDouble;
  5017. break;
  5018. default:
  5019. Fail("Invalid literal", literalExpr);
  5020. break;
  5021. }
  5022. }
  5023. void DbgExprEvaluator::Visit(BfCastExpression* castExpr)
  5024. {
  5025. mIsComplexExpression = true;
  5026. if (castExpr->mTypeRef == NULL)
  5027. return; // Error
  5028. AutocompleteCheckType(castExpr->mTypeRef);
  5029. auto resolvedType = ResolveTypeRef(castExpr->mTypeRef);
  5030. if (resolvedType == NULL)
  5031. return;
  5032. if (mExplicitThisExpr != NULL)
  5033. mDeferredInsertExplicitThisVector.push_back(NodeReplaceRecord(castExpr->mTypeRef, (BfAstNode**)&castExpr->mTypeRef));
  5034. mResult = CreateValueFromExpression(castExpr->mExpression);
  5035. if (!mResult)
  5036. return;
  5037. mResult = Cast(castExpr, mResult, resolvedType, true);
  5038. }
  5039. // We pass by reference to support "RAW" debug expression simplification
  5040. DbgTypedValue DbgExprEvaluator::CreateValueFromExpression(ASTREF(BfExpression*)& expr, DbgType* castToType, DbgEvalExprFlags flags)
  5041. {
  5042. //
  5043. {
  5044. BP_ZONE("DbgExprEvaluator::CreateValueFromExpression:CheckStack");
  5045. StackHelper stackHelper;
  5046. if (!stackHelper.CanStackExpand(64 * 1024))
  5047. {
  5048. DbgTypedValue result;
  5049. if (!stackHelper.Execute([&]()
  5050. {
  5051. result = CreateValueFromExpression(expr, castToType, flags);
  5052. }))
  5053. {
  5054. Fail("Expression too complex", expr);
  5055. }
  5056. return result;
  5057. }
  5058. }
  5059. mExpectingType = castToType;
  5060. VisitChild(expr);
  5061. GetResult();
  5062. auto result = mResult;
  5063. if ((result) && (castToType != NULL) && ((flags & DbgEvalExprFlags_NoCast) == 0))
  5064. result = Cast(expr, result, castToType, false);
  5065. mResult = DbgTypedValue();
  5066. if ((result.mHasNoValue) && ((flags & DbgEvalExprFlags_AllowTypeResult) == 0))
  5067. Fail("Value expected", expr);
  5068. return result;
  5069. }
  5070. void DbgExprEvaluator::PerformBinaryOperation(ASTREF(BfExpression*)& leftExpression, ASTREF(BfExpression*)& rightExpression, BfBinaryOp binaryOp, BfTokenNode* opToken, bool forceLeftType)
  5071. {
  5072. DbgTypedValue leftValue;
  5073. if (leftExpression != NULL)
  5074. leftValue = CreateValueFromExpression(leftExpression, mExpectingType, DbgEvalExprFlags_NoCast);
  5075. DbgTypedValue rightValue;
  5076. if (rightExpression == NULL)
  5077. {
  5078. return;
  5079. }
  5080. if (!leftValue)
  5081. {
  5082. VisitChild(rightExpression);
  5083. return;
  5084. }
  5085. leftValue.mType = leftValue.mType->RemoveModifiers();
  5086. /*if (leftValue.mType->IsRef())
  5087. leftValue.mType = leftValue.mType->GetUnderlyingType();*/
  5088. if ((binaryOp == BfBinaryOp_ConditionalAnd) || (binaryOp == BfBinaryOp_ConditionalOr))
  5089. {
  5090. bool isAnd = binaryOp == BfBinaryOp_ConditionalAnd;
  5091. if (!leftValue.mType->IsBoolean())
  5092. {
  5093. Fail(StrFormat("Operator requires boolean operand. Left hand side is '%s", leftValue.mType->ToString().c_str()), opToken);
  5094. return;
  5095. }
  5096. auto boolType = leftValue.mType;
  5097. if (isAnd)
  5098. {
  5099. if (!leftValue.mBool)
  5100. {
  5101. mResult = leftValue;
  5102. return;
  5103. }
  5104. rightValue = CreateValueFromExpression(rightExpression);
  5105. if (rightValue)
  5106. rightValue = Cast(rightExpression, rightValue, boolType);
  5107. mResult = rightValue;
  5108. }
  5109. else
  5110. {
  5111. if (leftValue.mBool)
  5112. {
  5113. mResult = leftValue;
  5114. return;
  5115. }
  5116. rightValue = CreateValueFromExpression(rightExpression);
  5117. if (rightValue)
  5118. rightValue = Cast(rightExpression, rightValue, boolType);
  5119. mResult = rightValue;
  5120. }
  5121. return;
  5122. }
  5123. if ((binaryOp == BfBinaryOp_NullCoalesce) && ((leftValue.mType->IsPointer()) || (leftValue.mType->IsBfObject())))
  5124. {
  5125. if (leftValue.mPtr != 0)
  5126. {
  5127. mResult = leftValue;
  5128. return;
  5129. }
  5130. CreateValueFromExpression(rightExpression, leftValue.mType);
  5131. return;
  5132. }
  5133. rightValue = CreateValueFromExpression(rightExpression, mExpectingType, DbgEvalExprFlags_NoCast);
  5134. if ((!leftValue) || (!rightValue))
  5135. return;
  5136. rightValue.mType = rightValue.mType->RemoveModifiers();
  5137. if (leftValue.mType->IsTypedPrimitive())
  5138. leftValue.mType = leftValue.mType->GetUnderlyingType();
  5139. if (rightValue.mType->IsTypedPrimitive())
  5140. rightValue.mType = rightValue.mType->GetUnderlyingType();
  5141. // Prefer floats, prefer unsigned
  5142. int leftCompareSize = leftValue.mType->GetByteCount();
  5143. if (leftValue.mType->IsFloat())
  5144. leftCompareSize += 16;
  5145. if (!leftValue.mType->IsPrimitiveType())
  5146. leftCompareSize += 0x100;
  5147. if ((leftValue.mIsLiteral) && (leftValue.mType->IsPointer()))
  5148. leftCompareSize += 0x200;
  5149. int rightCompareSize = rightValue.mType->GetByteCount();
  5150. if (rightValue.mType->IsFloat())
  5151. rightCompareSize += 16;
  5152. if (!rightValue.mType->IsPrimitiveType())
  5153. rightCompareSize += 0x100;
  5154. if ((rightValue.mIsLiteral) && (rightValue.mType->IsPointer()))
  5155. rightCompareSize += 0x200;
  5156. /*if ((leftValue.mType->IsTypedPrimitive()) && (rightValue.mType->IsTypedPrimitive()))
  5157. {
  5158. int leftInheritDepth = leftValue.mType->ToTypeInstance()->mInheritDepth;
  5159. int rightInheritDepth = rightValue.mType->ToTypeInstance()->mInheritDepth;
  5160. if (leftInheritDepth < rightInheritDepth)
  5161. {
  5162. // If both are typed primitives then choose the type with the lowest inherit depth
  5163. // so we will choose the base type when applicable
  5164. forceLeftType = true;
  5165. }
  5166. }*/
  5167. auto resultType = leftValue.mType;
  5168. if (!forceLeftType)
  5169. {
  5170. if ((resultType->IsNull()) ||
  5171. (rightCompareSize > leftCompareSize) ||
  5172. (((rightCompareSize == leftCompareSize) && (!rightValue.mType->IsSigned()))) ||
  5173. (rightValue.mType->IsTypedPrimitive()))
  5174. {
  5175. // Select the type with the "most information"
  5176. if (!rightValue.mType->IsNull())
  5177. resultType = rightValue.mType;
  5178. }
  5179. if ((!resultType->IsPointer()) && (rightValue.mType->IsPointer()))
  5180. resultType = rightValue.mType;
  5181. }
  5182. //bool explicitCast = false;
  5183. bool explicitCast = true;
  5184. DbgTypedValue* resultTypedValue;
  5185. DbgTypedValue* otherTypedValue;
  5186. DbgType* otherType;
  5187. BfAstNode* resultTypeSrc;
  5188. BfAstNode* otherTypeSrc;
  5189. if (resultType == leftValue.mType)
  5190. {
  5191. resultTypedValue = &leftValue;
  5192. resultTypeSrc = leftExpression;
  5193. otherTypedValue = &rightValue;
  5194. otherTypeSrc = rightExpression;
  5195. otherType = otherTypedValue->mType;
  5196. }
  5197. else
  5198. {
  5199. resultTypedValue = &rightValue;
  5200. resultTypeSrc = rightExpression;
  5201. otherTypedValue = &leftValue;
  5202. otherTypeSrc = leftExpression;
  5203. otherType = otherTypedValue->mType;
  5204. }
  5205. if ((resultTypedValue->mIsLiteral) && (resultType->IsPointer()))
  5206. {
  5207. // If we're comparing against a string literal like 'str == "Hey!"', handle that
  5208. if (BfBinOpEqualityCheck(binaryOp))
  5209. {
  5210. DbgType* useType = otherType;
  5211. useType = useType->RemoveModifiers();
  5212. if (useType->IsPointer())
  5213. useType = useType->mTypeParam;
  5214. DbgTypedValue useTypedValue = *otherTypedValue;
  5215. if (useTypedValue.mType->IsPointer())
  5216. {
  5217. useTypedValue.mSrcAddress = useTypedValue.mPtr;
  5218. useTypedValue.mType = useTypedValue.mType->mTypeParam;
  5219. }
  5220. auto language = useType->GetLanguage();
  5221. auto dbgCompileUnit = useType->mCompileUnit;
  5222. auto dbgModule = useType->GetDbgModule();
  5223. Array<String> dbgVisWildcardCaptures;
  5224. auto debugVis = mDebugger->FindVisualizerForType(useType, &dbgVisWildcardCaptures);
  5225. if (debugVis != NULL)
  5226. {
  5227. auto& displayStringList = debugVis->mStringViews;
  5228. String displayString;
  5229. for (auto displayEntry : displayStringList)
  5230. {
  5231. auto& displayStringList = debugVis->mStringViews;
  5232. DwFormatInfo formatInfo;
  5233. formatInfo.mRawString = true;
  5234. formatInfo.mLanguage = language;
  5235. if (!displayEntry->mCondition.empty())
  5236. {
  5237. if (!mDebugger->EvalCondition(debugVis, dbgCompileUnit, useTypedValue, formatInfo, displayEntry->mCondition, dbgVisWildcardCaptures, displayString))
  5238. continue;
  5239. }
  5240. String displayStr = mDebugger->mDebugManager->mDebugVisualizers->DoStringReplace(displayEntry->mString, dbgVisWildcardCaptures);
  5241. mDebugger->ProcessEvalString(dbgCompileUnit, useTypedValue, displayStr, displayString, formatInfo, debugVis, false);
  5242. bool isEq = displayString == resultTypedValue->mCharPtr;
  5243. auto boolType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5244. mResult.mType = boolType;
  5245. mResult.mBool = isEq == ((binaryOp == BfBinaryOp_Equality) || (binaryOp == BfBinaryOp_StrictEquality));
  5246. return;
  5247. }
  5248. }
  5249. }
  5250. Fail("Cannot perform operation with a literal value", resultTypeSrc);
  5251. return;
  5252. }
  5253. DbgTypedValue convLeftValue;
  5254. DbgTypedValue convRightValue;
  5255. /*if ((resultType->IsVar()) || (otherType->IsVar()))
  5256. {
  5257. mResult = DbgTypedValue(mModule->GetDefaultValue(resultType), resultType);
  5258. return;
  5259. }*/
  5260. if ((otherType->IsNull()) && BfBinOpEqualityCheck(binaryOp))
  5261. {
  5262. bool isEquality = (binaryOp == BfBinaryOp_Equality) || (binaryOp == BfBinaryOp_StrictEquality);
  5263. if (resultType->IsValueType())
  5264. {
  5265. /*if (!mModule->IsInSpecializedGeneric())
  5266. {
  5267. //CS0472: The result of the expression is always 'true' since a value of type 'int' is never equal to 'null' of type '<null>'
  5268. mModule->mCompiler->mPassInstance->Warn(BfWarning_CS0472_ValueTypeNullCompare,
  5269. StrFormat("The result of the expression is always '%s' since a value of type '%s' can never be null",
  5270. isEquality ? "false" : "true", mModule->TypeToString(resultType).c_str()), otherTypeSrc);
  5271. }*/
  5272. // Valuetypes never equal null
  5273. auto boolType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5274. mResult.mType = boolType;
  5275. mResult.mBool = !isEquality;
  5276. return;
  5277. }
  5278. }
  5279. //TODO: Use operator methods?
  5280. /*if ((leftValue.mType->IsTypeInstance()) || (rightValue.mType->IsTypeInstance()))
  5281. {
  5282. SmallVector<BfResolvedArg, 2> args;
  5283. BfResolvedArg leftArg;
  5284. leftArg.mExpression = leftExpression;
  5285. leftArg.mTypedValue = leftValue;
  5286. args.push_back(leftArg);
  5287. BfResolvedArg rightArg;
  5288. rightArg.mExpression = rightExpression;
  5289. rightArg.mTypedValue = rightValue;
  5290. args.push_back(rightArg);
  5291. BfMethodMatcher methodMatcher(opToken, mModule, "", args, NULL);
  5292. BfBaseClassWalker baseClassWalker(leftValue.mType->ToTypeInstance(), rightValue.mType->ToTypeInstance());
  5293. bool invertResult = false;
  5294. while (auto checkType = baseClassWalker.Next())
  5295. {
  5296. BfOperatorDef* oppositeOperatorDef = NULL;
  5297. BfBinaryOp oppositeBinaryOp = GetOppositeBinaryOp(binaryOp);
  5298. for (auto operatorDef : checkType->mTypeDef->mOperators)
  5299. {
  5300. if (operatorDef->mOperatorDeclaration->mBinOp == binaryOp)
  5301. methodMatcher.CheckMethod(checkType, operatorDef);
  5302. else if (operatorDef->mOperatorDeclaration->mBinOp == oppositeBinaryOp)
  5303. oppositeOperatorDef = operatorDef;
  5304. }
  5305. if ((methodMatcher.mBestMethodDef == NULL) && (oppositeOperatorDef != NULL))
  5306. {
  5307. if (methodMatcher.CheckMethod(checkType, oppositeOperatorDef))
  5308. invertResult = true;
  5309. }
  5310. }
  5311. if (methodMatcher.mBestMethodDef != NULL)
  5312. {
  5313. SetElementType(opToken, BfSourceElementType_Method);
  5314. mResult = CreateCall(&methodMatcher, DbgTypedValue());
  5315. if ((invertResult) && (mResult.mType == mModule->GetPrimitiveType(BfTypeCode_Boolean)))
  5316. mResult.mValue = mModule->mIRBuilder->CreateNot(mResult.mValue);
  5317. return;
  5318. }
  5319. }*/
  5320. if (resultType->IsPointer() && otherType->IsPointer())
  5321. {
  5322. //TODO: Allow all pointer comparisons, but only allow SUBTRACTION between equal pointer types
  5323. if (binaryOp == BfBinaryOp_Subtract)
  5324. {
  5325. if (!resultType->Equals(otherType))
  5326. {
  5327. Fail(StrFormat("Operands must be the same type, '%s' doesn't match '%s'",
  5328. leftValue.mType->ToString().c_str(), rightValue.mType->ToString().c_str()),
  5329. opToken);
  5330. return;
  5331. }
  5332. DbgType* intPtrType = mDbgModule->GetPrimitiveType(DbgType_IntPtr_Alias, GetLanguage());
  5333. long ptrDiff = leftValue.mPtr - rightValue.mPtr;
  5334. int elemSize = resultType->mTypeParam->GetStride();
  5335. if (elemSize == 0)
  5336. {
  5337. Fail("Invalid operation on void values", opToken);
  5338. return;
  5339. }
  5340. //BF_ASSERT((ptrDiff % elemSize) == 0);
  5341. mResult.mInt64 = ptrDiff / elemSize;
  5342. mResult.mType = intPtrType;
  5343. return;
  5344. }
  5345. else if ((binaryOp != BfBinaryOp_Equality) && (binaryOp != BfBinaryOp_StrictEquality) &
  5346. (binaryOp != BfBinaryOp_InEquality) && (binaryOp != BfBinaryOp_StrictInEquality) &&
  5347. (binaryOp != BfBinaryOp_LessThan) && (binaryOp != BfBinaryOp_LessThanOrEqual) &&
  5348. (binaryOp != BfBinaryOp_GreaterThan) && (binaryOp != BfBinaryOp_GreaterThanOrEqual))
  5349. {
  5350. Fail("Invalid operation on pointers", opToken);
  5351. return;
  5352. }
  5353. // Compare them as ints
  5354. resultType = mDbgModule->GetPrimitiveType(DbgType_UIntPtr_Alias, GetLanguage());
  5355. explicitCast = true;
  5356. }
  5357. else if (resultType->IsPointer())
  5358. {
  5359. if (otherType->IsNull())
  5360. {
  5361. if (!BfBinOpEqualityCheck(binaryOp))
  5362. {
  5363. Fail(StrFormat("Invalid operation between '%s' and null", resultType->ToString().c_str()), opToken);
  5364. return;
  5365. }
  5366. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5367. if (binaryOp == BfBinaryOp_Equality)
  5368. mResult.mBool = resultTypedValue->mPtr == NULL;
  5369. else
  5370. mResult.mBool = resultTypedValue->mPtr != NULL;
  5371. return;
  5372. }
  5373. bool isCompare = (binaryOp >= BfBinaryOp_Equality) && (binaryOp <= BfBinaryOp_LessThanOrEqual);
  5374. // One pointer
  5375. if ((!otherType->IsInteger()) ||
  5376. ((binaryOp != BfBinaryOp_Add) && (binaryOp != BfBinaryOp_Subtract) && (binaryOp != BfBinaryOp_OverflowAdd) && (binaryOp != BfBinaryOp_OverflowSubtract) && (!isCompare)))
  5377. {
  5378. Fail("Can only add or subtract integer values from pointers", rightExpression);
  5379. return;
  5380. }
  5381. if ((binaryOp == BfBinaryOp_Add) || (binaryOp == BfBinaryOp_Subtract) || (binaryOp == BfBinaryOp_OverflowAdd) || (binaryOp == BfBinaryOp_OverflowSubtract))
  5382. {
  5383. auto underlyingType = otherType->GetUnderlyingType();
  5384. mResult.mType = resultType;
  5385. DbgType* innerType = resultType->mTypeParam;
  5386. if (binaryOp == BfBinaryOp_Subtract)
  5387. {
  5388. if (resultTypeSrc == rightExpression)
  5389. Fail("Cannot subtract a pointer from an integer", resultTypeSrc);
  5390. mResult.mPtr = resultTypedValue->mPtr - otherTypedValue->GetInt64() * innerType->GetStride();
  5391. }
  5392. else
  5393. {
  5394. mResult.mPtr = resultTypedValue->mPtr + otherTypedValue->GetInt64() * innerType->GetStride();
  5395. }
  5396. if (innerType->GetByteCount() == 0)
  5397. {
  5398. Warn("Adding to a pointer to a zero-sized element has no effect", opToken);
  5399. }
  5400. return;
  5401. }
  5402. }
  5403. if ((resultType->IsPointer()) || (resultType->IsBfObject()) || (resultType->IsInterface()) /*|| (resultType->IsGenericParam())*/)
  5404. {
  5405. if (!BfBinOpEqualityCheck(binaryOp))
  5406. {
  5407. if (resultType->IsPointer())
  5408. Fail("Invalid operation for pointers", opToken);
  5409. else
  5410. Fail("Invalid operation for objects", opToken);
  5411. return;
  5412. }
  5413. if (otherType->IsNull())
  5414. {
  5415. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5416. if ((binaryOp == BfBinaryOp_Equality) || (binaryOp == BfBinaryOp_StrictEquality))
  5417. mResult.mBool = resultTypedValue->mPtr == NULL;
  5418. else
  5419. mResult.mBool = resultTypedValue->mPtr != NULL;
  5420. }
  5421. else
  5422. {
  5423. bool explicitCast = true;
  5424. if (otherType->IsInteger())
  5425. explicitCast = true;
  5426. auto convertedValue = Cast(otherTypeSrc, *otherTypedValue, resultType, explicitCast);
  5427. if (!convertedValue)
  5428. return;
  5429. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5430. if ((binaryOp == BfBinaryOp_Equality) || (binaryOp == BfBinaryOp_StrictEquality))
  5431. mResult.mBool = resultTypedValue->mPtr == convertedValue.mPtr;
  5432. else
  5433. mResult.mBool = resultTypedValue->mPtr != convertedValue.mPtr;
  5434. }
  5435. return;
  5436. }
  5437. /*else if (resultType->IsTypedPrimitive())
  5438. {
  5439. bool needsOtherCast = true;
  5440. if (otherType != resultType)
  5441. {
  5442. if (otherType->IsPrimitiveType())
  5443. {
  5444. // Allow zero comparisons to match all typed primitives
  5445. if ((binaryOp == BfBinaryOp_Equality) || (binaryOp == BfBinaryOp_InEquality))
  5446. {
  5447. auto intConstant = dyn_cast<ConstantInt>(otherTypedValue->mValue);
  5448. if (intConstant != NULL)
  5449. {
  5450. if (intConstant->getSExtValue() == 0)
  5451. {
  5452. needsOtherCast = false;
  5453. }
  5454. }
  5455. }
  5456. }
  5457. if (needsOtherCast)
  5458. {
  5459. // The only purpose of this cast is to potentially throw a casting error
  5460. Value* otherCastResult = mModule->CastToValue(otherTypeSrc, *otherTypedValue, resultType, explicitCast);
  5461. if (otherCastResult == NULL)
  5462. return;
  5463. }
  5464. }
  5465. auto underlyingType = resultType->GetUnderlyingType();
  5466. Value* convResultValue = mModule->CastToValue(resultTypeSrc, *resultTypedValue, underlyingType, true);
  5467. Value* convOtherValue = mModule->CastToValue(otherTypeSrc, *otherTypedValue, underlyingType, true);
  5468. if ((!underlyingType->IsValuelessType()) && ((convResultValue == NULL) || (convOtherValue == NULL)))
  5469. return;
  5470. if (resultTypedValue == &leftValue)
  5471. PerformBinaryOperation(underlyingType, convResultValue, convOtherValue, binaryOp, opToken);
  5472. else
  5473. PerformBinaryOperation(underlyingType, convOtherValue, convResultValue, binaryOp, opToken);
  5474. if (mResult.mType == underlyingType)
  5475. mResult.mType = resultType;
  5476. return;
  5477. }*/
  5478. else if (((leftValue.mType->IsStruct()) || (leftValue.mType->IsBfObject())) && (!resultType->IsEnum()))
  5479. {
  5480. if (leftValue.mType == rightValue.mType)
  5481. {
  5482. Fail(StrFormat("Operator '%s' cannot be applied to operands of type '%s'",
  5483. opToken->ToString().c_str(),
  5484. TypeToString(leftValue.mType).c_str()), opToken);
  5485. }
  5486. else
  5487. {
  5488. Fail(StrFormat("Operator '%s' cannot be applied to operands of type '%s' and '%s'",
  5489. opToken->ToString().c_str(),
  5490. TypeToString(leftValue.mType).c_str(),
  5491. TypeToString(rightValue.mType).c_str()), opToken);
  5492. }
  5493. return;
  5494. }
  5495. if ((resultType->IsInteger()) && (!forceLeftType))
  5496. {
  5497. bool isBitwiseExpr =
  5498. (binaryOp == BfBinaryOp_BitwiseAnd) |
  5499. (binaryOp == BfBinaryOp_BitwiseOr) |
  5500. (binaryOp == BfBinaryOp_ExclusiveOr) |
  5501. (binaryOp == BfBinaryOp_LeftShift) |
  5502. (binaryOp == BfBinaryOp_RightShift);
  5503. // For binary expressions we don't promote to 'int' unless the types don't match
  5504. if ((!isBitwiseExpr) || (leftValue.mType != rightValue.mType))
  5505. {
  5506. if (binaryOp == BfBinaryOp_Subtract)
  5507. {
  5508. }
  5509. else if (resultType->GetByteCount() < 4)
  5510. {
  5511. resultType = mDbgModule->GetPrimitiveType(DbgType_i32, GetLanguage());
  5512. }
  5513. else if (leftValue.mType != rightValue.mType)
  5514. {
  5515. if ((binaryOp == BfBinaryOp_LeftShift) || (binaryOp == BfBinaryOp_RightShift))
  5516. {
  5517. // For shifts we leave it in the target type if we're already at 'int' or higher
  5518. }
  5519. else if ((!resultType->IsSigned()) && (otherType->IsSigned()))
  5520. {
  5521. /*if (CanCast(*otherTypedValue, resultType))
  5522. {
  5523. // If we can convert the 'other' value implicitly then it's a convertible literal, leave as uint
  5524. }
  5525. else if (resultType->mSize == 4)
  5526. {
  5527. resultType = mDbgModule->GetPrimitiveType(DbgType_i64);
  5528. }
  5529. else
  5530. {
  5531. Fail(StrFormat("Operator cannot be applied to operands of type '%s' and '%s'",
  5532. TypeToString(leftValue.mType).c_str(),
  5533. TypeToString(rightValue.mType).c_str()), opToken);
  5534. return;
  5535. }*/
  5536. explicitCast = true;
  5537. }
  5538. }
  5539. }
  5540. }
  5541. if (convLeftValue == NULL)
  5542. convLeftValue = Cast(leftExpression, leftValue, resultType, explicitCast);
  5543. if (convRightValue == NULL)
  5544. convRightValue = Cast(rightExpression, rightValue, resultType, explicitCast);
  5545. PerformBinaryOperation(resultType, convLeftValue, convRightValue, binaryOp, opToken);
  5546. }
  5547. void DbgExprEvaluator::PerformBinaryOperation(DbgType* resultType, DbgTypedValue convLeftValue, DbgTypedValue convRightValue, BfBinaryOp binaryOp, BfTokenNode* opToken)
  5548. {
  5549. if (resultType->IsValuelessType())
  5550. {
  5551. switch (binaryOp)
  5552. {
  5553. case BfBinaryOp_Equality:
  5554. case BfBinaryOp_StrictEquality:
  5555. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5556. mResult.mBool = true;
  5557. break;
  5558. case BfBinaryOp_InEquality:
  5559. case BfBinaryOp_StrictInEquality:
  5560. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5561. mResult.mBool = false;
  5562. break;
  5563. default:
  5564. Fail("Invalid operation for void", opToken);
  5565. break;
  5566. }
  5567. return;
  5568. }
  5569. if ((convLeftValue == NULL) || (convRightValue == NULL))
  5570. return;
  5571. if ((resultType->IsEnum()) || (resultType->IsTypedPrimitive()))
  5572. resultType = resultType->GetUnderlyingType();
  5573. if (resultType->IsPrimitiveType())
  5574. {
  5575. auto primType = resultType;
  5576. if (primType->mTypeCode == DbgType_Bool)
  5577. {
  5578. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5579. switch (binaryOp)
  5580. {
  5581. case BfBinaryOp_Equality:
  5582. case BfBinaryOp_StrictEquality:
  5583. mResult.mBool = convLeftValue.mBool == convRightValue.mBool;
  5584. break;
  5585. case BfBinaryOp_InEquality:
  5586. case BfBinaryOp_StrictInEquality:
  5587. mResult.mBool = convLeftValue.mBool != convRightValue.mBool;
  5588. break;
  5589. case BfBinaryOp_ConditionalAnd:
  5590. mResult.mBool = convLeftValue.mBool && convRightValue.mBool;
  5591. break;
  5592. case BfBinaryOp_ConditionalOr:
  5593. mResult.mBool = convLeftValue.mBool | convRightValue.mBool;
  5594. break;
  5595. case BfBinaryOp_ExclusiveOr:
  5596. mResult.mBool = convLeftValue.mBool ^ convRightValue.mBool;
  5597. break;
  5598. default:
  5599. Fail("Invalid operation for booleans", opToken);
  5600. break;
  5601. }
  5602. return;
  5603. }
  5604. }
  5605. if ((!resultType->IsIntegral()) && (!resultType->IsFloat()))
  5606. {
  5607. Fail(StrFormat("Cannot perform operation on type '%s'", TypeToString(resultType).c_str()), opToken);
  5608. return;
  5609. }
  5610. mResult.mType = resultType;
  5611. if (resultType->IsInteger())
  5612. {
  5613. switch (binaryOp)
  5614. {
  5615. case BfBinaryOp_BitwiseAnd:
  5616. mResult.mInt64 = convLeftValue.GetInt64() & convRightValue.GetInt64();
  5617. return;
  5618. case BfBinaryOp_BitwiseOr:
  5619. mResult.mInt64 = convLeftValue.GetInt64() | convRightValue.GetInt64();
  5620. return;
  5621. case BfBinaryOp_ExclusiveOr:
  5622. mResult.mInt64 = convLeftValue.GetInt64() ^ convRightValue.GetInt64();
  5623. return;
  5624. case BfBinaryOp_LeftShift:
  5625. mResult.mInt64 = convLeftValue.GetInt64() << convRightValue.GetInt64();
  5626. return;
  5627. case BfBinaryOp_RightShift:
  5628. mResult.mInt64 = convLeftValue.GetInt64() >> convRightValue.GetInt64();
  5629. return;
  5630. }
  5631. }
  5632. switch (binaryOp)
  5633. {
  5634. case BfBinaryOp_Add:
  5635. case BfBinaryOp_OverflowAdd:
  5636. if (resultType->mTypeCode == DbgType_Single)
  5637. mResult.mSingle = convLeftValue.mSingle + convRightValue.mSingle;
  5638. else if (resultType->mTypeCode == DbgType_Double)
  5639. mResult.mDouble = convLeftValue.mDouble + convRightValue.mDouble;
  5640. else
  5641. mResult.mInt64 = convLeftValue.GetInt64() + convRightValue.GetInt64();
  5642. break;
  5643. case BfBinaryOp_Subtract:
  5644. case BfBinaryOp_OverflowSubtract:
  5645. if (resultType->mTypeCode == DbgType_Single)
  5646. mResult.mSingle = convLeftValue.mSingle - convRightValue.mSingle;
  5647. else if (resultType->mTypeCode == DbgType_Double)
  5648. mResult.mDouble = convLeftValue.mDouble - convRightValue.mDouble;
  5649. else
  5650. mResult.mInt64 = convLeftValue.GetInt64() - convRightValue.GetInt64();
  5651. break;
  5652. case BfBinaryOp_Multiply:
  5653. case BfBinaryOp_OverflowMultiply:
  5654. if (resultType->mTypeCode == DbgType_Single)
  5655. mResult.mSingle = convLeftValue.mSingle * convRightValue.mSingle;
  5656. else if (resultType->mTypeCode == DbgType_Double)
  5657. mResult.mDouble = convLeftValue.mDouble * convRightValue.mDouble;
  5658. else
  5659. mResult.mInt64 = convLeftValue.GetInt64() * convRightValue.GetInt64();
  5660. break;
  5661. case BfBinaryOp_Divide:
  5662. {
  5663. bool isZero = false;
  5664. if (resultType->mTypeCode == DbgType_Single)
  5665. {
  5666. mResult.mSingle = convLeftValue.mSingle / convRightValue.mSingle;
  5667. }
  5668. else if (resultType->mTypeCode == DbgType_Double)
  5669. {
  5670. mResult.mDouble = convLeftValue.mDouble / convRightValue.mDouble;
  5671. }
  5672. else
  5673. {
  5674. if (convRightValue.GetInt64() == 0)
  5675. isZero = true;
  5676. else
  5677. mResult.mInt64 = convLeftValue.GetInt64() / convRightValue.GetInt64();
  5678. }
  5679. if (isZero)
  5680. Fail("Divide by zero", opToken);
  5681. }
  5682. break;
  5683. case BfBinaryOp_Modulus:
  5684. {
  5685. bool isZero = false;
  5686. if (resultType->mTypeCode == DbgType_Single)
  5687. mResult.mSingle = fmod(convLeftValue.mSingle, convRightValue.mSingle);
  5688. else if (resultType->mTypeCode == DbgType_Double)
  5689. mResult.mDouble = fmod(convLeftValue.mDouble, convRightValue.mDouble);
  5690. else
  5691. {
  5692. if (convRightValue.GetInt64() == 0)
  5693. isZero = true;
  5694. else
  5695. mResult.mInt64 = convLeftValue.GetInt64() % convRightValue.GetInt64();
  5696. }
  5697. if (isZero)
  5698. Fail("Divide by zero", opToken);
  5699. }
  5700. break;
  5701. case BfBinaryOp_Equality:
  5702. case BfBinaryOp_StrictEquality:
  5703. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5704. if (resultType->mTypeCode == DbgType_Single)
  5705. mResult.mBool = convLeftValue.mSingle == convRightValue.mSingle;
  5706. else if (resultType->mTypeCode == DbgType_Double)
  5707. mResult.mBool = convLeftValue.mDouble == convRightValue.mDouble;
  5708. else
  5709. mResult.mBool = convLeftValue.GetInt64() == convRightValue.GetInt64();
  5710. break;
  5711. case BfBinaryOp_InEquality:
  5712. case BfBinaryOp_StrictInEquality:
  5713. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5714. if (resultType->mTypeCode == DbgType_Single)
  5715. mResult.mBool = convLeftValue.mSingle != convRightValue.mSingle;
  5716. else if (resultType->mTypeCode == DbgType_Double)
  5717. mResult.mBool = convLeftValue.mDouble != convRightValue.mDouble;
  5718. else
  5719. mResult.mBool = convLeftValue.GetInt64() != convRightValue.GetInt64();
  5720. break;
  5721. case BfBinaryOp_LessThan:
  5722. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5723. if (resultType->mTypeCode == DbgType_Single)
  5724. mResult.mBool = convLeftValue.mSingle < convRightValue.mSingle;
  5725. else if (resultType->mTypeCode == DbgType_Double)
  5726. mResult.mBool = convLeftValue.mDouble < convRightValue.mDouble;
  5727. else
  5728. mResult.mBool = convLeftValue.GetInt64() < convRightValue.GetInt64();
  5729. break;
  5730. case BfBinaryOp_LessThanOrEqual:
  5731. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5732. if (resultType->mTypeCode == DbgType_Single)
  5733. mResult.mBool = convLeftValue.mSingle <= convRightValue.mSingle;
  5734. else if (resultType->mTypeCode == DbgType_Double)
  5735. mResult.mBool = convLeftValue.mDouble <= convRightValue.mDouble;
  5736. else
  5737. mResult.mBool = convLeftValue.GetInt64() <= convRightValue.GetInt64();
  5738. break;
  5739. case BfBinaryOp_GreaterThan:
  5740. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5741. if (resultType->mTypeCode == DbgType_Single)
  5742. mResult.mBool = convLeftValue.mSingle > convRightValue.mSingle;
  5743. else if (resultType->mTypeCode == DbgType_Double)
  5744. mResult.mBool = convLeftValue.mDouble > convRightValue.mDouble;
  5745. else
  5746. mResult.mBool = convLeftValue.GetInt64() > convRightValue.GetInt64();
  5747. break;
  5748. case BfBinaryOp_GreaterThanOrEqual:
  5749. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5750. if (resultType->mTypeCode == DbgType_Single)
  5751. mResult.mBool = convLeftValue.mSingle >= convRightValue.mSingle;
  5752. else if (resultType->mTypeCode == DbgType_Double)
  5753. mResult.mBool = convLeftValue.mDouble >= convRightValue.mDouble;
  5754. else
  5755. mResult.mBool = convLeftValue.GetInt64() >= convRightValue.GetInt64();
  5756. break;
  5757. default:
  5758. Fail("Invalid operation", opToken);
  5759. break;
  5760. }
  5761. }
  5762. void DbgExprEvaluator::Visit(BfBinaryOperatorExpression* binOpExpr)
  5763. {
  5764. //mIsComplexExpression = true;
  5765. //PerformBinaryOperation(binOpExpr->mLeft, binOpExpr->mRight, binOpExpr->mOp, binOpExpr->mOpToken, false);
  5766. // Check for "(double)-1.0" style cast, misidentified as a binary operation
  5767. if ((binOpExpr->mOp == BfBinaryOp_Add) || (binOpExpr->mOp == BfBinaryOp_Subtract) ||
  5768. (binOpExpr->mOp == BfBinaryOp_BitwiseAnd) || (binOpExpr->mOp == BfBinaryOp_Multiply))
  5769. {
  5770. if (auto parenExpr = BfNodeDynCast<BfParenthesizedExpression>(binOpExpr->mLeft))
  5771. {
  5772. BfAstNode* castTypeExpr = BfNodeDynCast<BfIdentifierNode>(parenExpr->mExpression);
  5773. if (castTypeExpr == NULL)
  5774. castTypeExpr = BfNodeDynCast<BfMemberReferenceExpression>(parenExpr->mExpression);
  5775. if (castTypeExpr != NULL)
  5776. {
  5777. SetAndRestoreValue<bool> prevIgnoreError(mIgnoreErrors, true);
  5778. auto resolvedType = ResolveTypeRef(castTypeExpr);
  5779. prevIgnoreError.Restore();
  5780. if (resolvedType != NULL)
  5781. {
  5782. if (binOpExpr->mOp == BfBinaryOp_BitwiseAnd)
  5783. {
  5784. PerformUnaryExpression(binOpExpr->mOpToken, BfUnaryOp_AddressOf, binOpExpr->mRight);
  5785. }
  5786. else if (binOpExpr->mOp == BfBinaryOp_Multiply)
  5787. {
  5788. PerformUnaryExpression(binOpExpr->mOpToken, BfUnaryOp_Dereference, binOpExpr->mRight);
  5789. }
  5790. else
  5791. {
  5792. VisitChild(binOpExpr->mRight);
  5793. if (!mResult)
  5794. return;
  5795. }
  5796. if ((mResult) && (binOpExpr->mOp == BfBinaryOp_Subtract))
  5797. {
  5798. if (mResult.mType->mTypeCode == DbgType_Single)
  5799. mResult.mSingle = -mResult.mSingle;
  5800. else if (mResult.mType->mTypeCode == DbgType_Double)
  5801. mResult.mDouble = -mResult.mDouble;
  5802. else
  5803. mResult.mInt64 = -mResult.GetInt64();
  5804. }
  5805. mResult = Cast(binOpExpr, mResult, resolvedType, true);
  5806. return;
  5807. }
  5808. }
  5809. }
  5810. }
  5811. if (binOpExpr->mRight == NULL)
  5812. {
  5813. //mModule->AssertErrorState();
  5814. // We visit the children for autocompletion only
  5815. if (binOpExpr->mLeft != NULL)
  5816. VisitChild(binOpExpr->mLeft);
  5817. if (mResult)
  5818. {
  5819. //if (mAutoComplete != NULL)
  5820. //mAutoComplete->CheckEmptyStart(binOpExpr->mOpToken, mResult.mType);
  5821. }
  5822. if (binOpExpr->mRight != NULL)
  5823. VisitChild(binOpExpr->mRight);
  5824. return;
  5825. }
  5826. PerformBinaryOperation(binOpExpr->mLeft, binOpExpr->mRight, binOpExpr->mOp, binOpExpr->mOpToken, false);
  5827. }
  5828. void DbgExprEvaluator::PerformUnaryExpression(BfAstNode* opToken, BfUnaryOp unaryOp, ASTREF(BfExpression*)& expr)
  5829. {
  5830. if (unaryOp != BfUnaryOp_Dereference)
  5831. mIsComplexExpression = true;
  5832. VisitChild(expr);
  5833. GetResult();
  5834. if (!mResult)
  5835. return;
  5836. bool wasLiteral = mResult.mIsLiteral;
  5837. mResult.mIsLiteral = false;
  5838. switch (unaryOp)
  5839. {
  5840. case BfUnaryOp_Decrement:
  5841. case BfUnaryOp_PostDecrement:
  5842. case BfUnaryOp_Increment:
  5843. case BfUnaryOp_PostIncrement:
  5844. auto ptr = mResult;
  5845. ptr.mType = ptr.mType->RemoveModifiers();
  5846. if (ptr.mType->IsEnum())
  5847. ptr.mType = ptr.mType->mTypeParam;
  5848. auto val = mResult;
  5849. int add = ((unaryOp == BfUnaryOp_Decrement) || (unaryOp == BfUnaryOp_PostDecrement)) ? -1 : 1;
  5850. switch (ptr.mType->mTypeCode)
  5851. {
  5852. case DbgType_UChar:
  5853. case DbgType_SChar:
  5854. case DbgType_i8:
  5855. case DbgType_u8:
  5856. case DbgType_Utf8:
  5857. val.mUInt8 += add;
  5858. break;
  5859. case DbgType_UChar16:
  5860. case DbgType_SChar16:
  5861. case DbgType_i16:
  5862. case DbgType_u16:
  5863. case DbgType_Utf16:
  5864. val.mUInt16 += add;
  5865. break;
  5866. case DbgType_UChar32:
  5867. case DbgType_SChar32:
  5868. case DbgType_i32:
  5869. case DbgType_u32:
  5870. case DbgType_Utf32:
  5871. val.mUInt32 += add;
  5872. break;
  5873. case DbgType_i64:
  5874. case DbgType_u64:
  5875. val.mUInt64 += add;
  5876. break;
  5877. case DbgType_Single:
  5878. val.mSingle += add;
  5879. break;
  5880. case DbgType_Double:
  5881. val.mDouble += add;
  5882. break;
  5883. default:
  5884. Fail(StrFormat("Unable to perform operation on type '%s'", ptr.mType->ToString()), expr);
  5885. return;
  5886. }
  5887. if ((mExpressionFlags & DwEvalExpressionFlag_AllowSideEffects) == 0)
  5888. {
  5889. mBlockedSideEffects = true;
  5890. return;
  5891. }
  5892. else
  5893. {
  5894. StoreValue(mResult, val, opToken);
  5895. }
  5896. if ((unaryOp == BfUnaryOp_Decrement) || (unaryOp == BfUnaryOp_Increment))
  5897. mResult = val;
  5898. return;
  5899. }
  5900. bool numericFail = false;
  5901. switch (unaryOp)
  5902. {
  5903. case BfUnaryOp_Dereference:
  5904. {
  5905. auto type = mResult.mType->RemoveModifiers();
  5906. if (!type->IsPointer())
  5907. {
  5908. Fail("Operator can only be used on pointer values", opToken);
  5909. return;
  5910. }
  5911. mResult = ReadTypedValue(opToken, type->mTypeParam, mResult.mPtr, DbgAddrType_Target);
  5912. }
  5913. break;
  5914. case BfUnaryOp_AddressOf:
  5915. {
  5916. if ((mResult.mSrcAddress == 0) || (mResult.mSrcAddress == -1))
  5917. {
  5918. if (mResult.mRegNum != -1)
  5919. {
  5920. Fail(StrFormat("Cannot take address of register '%s'", CPURegisters::GetRegisterName(mResult.mRegNum)), opToken);
  5921. return;
  5922. }
  5923. Fail("Cannot take address of value", opToken);
  5924. return;
  5925. }
  5926. mResult.mType = mResult.mType->RemoveModifiers();
  5927. mResult.mType = mDbgModule->GetPointerType(mResult.mType);
  5928. mResult.mPtr = mResult.mSrcAddress;
  5929. mResult.mSrcAddress = 0;
  5930. }
  5931. break;
  5932. case BfUnaryOp_Not:
  5933. {
  5934. auto boolType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  5935. if (mResult.mType->mTypeCode != DbgType_Bool)
  5936. {
  5937. Fail("Operator can only be used on boolean values", opToken);
  5938. return;
  5939. }
  5940. mResult.mIsLiteral = wasLiteral;
  5941. mResult.mBool = !mResult.mBool;
  5942. }
  5943. break;
  5944. case BfUnaryOp_Negate:
  5945. {
  5946. if (mResult.mType->IsInteger())
  5947. {
  5948. auto primType = mResult.mType;
  5949. auto wantType = primType;
  5950. if (wasLiteral)
  5951. {
  5952. // This is a special case where the user entered -0x80000000 (maxint) but we thought "0x80000000" was a uint in the parser
  5953. // which would get expanded to an int64 for this negate. Properly bring back down to an int32
  5954. if ((primType->mTypeCode == DbgType_u32) && (mResult.GetInt64() == -0x80000000LL))
  5955. {
  5956. //mResult = DbgTypedValue(mModule->GetConstValue((int) i64Val), mModule->GetPrimitiveType(DwTypeCode_Int32));
  5957. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_i32, GetLanguage());
  5958. return;
  5959. }
  5960. }
  5961. if (!primType->IsSigned())
  5962. {
  5963. if (primType->mSize == 1)
  5964. wantType = mDbgModule->GetPrimitiveType(DbgType_i16, GetLanguage());
  5965. else if (primType->mSize == 2)
  5966. wantType = mDbgModule->GetPrimitiveType(DbgType_i32, GetLanguage());
  5967. else if (primType->mSize == 4)
  5968. wantType = mDbgModule->GetPrimitiveType(DbgType_i64, GetLanguage());
  5969. }
  5970. mResult.mIsLiteral = wasLiteral;
  5971. mResult.mInt64 = -mResult.GetInt64();
  5972. mResult.mType = wantType;
  5973. return;
  5974. }
  5975. mResult.mIsLiteral = wasLiteral;
  5976. if (mResult.mType->mTypeCode == DbgType_Single)
  5977. mResult.mSingle = -mResult.mSingle;
  5978. else if (mResult.mType->mTypeCode == DbgType_Double)
  5979. mResult.mDouble = -mResult.mDouble;
  5980. else
  5981. numericFail = true;
  5982. }
  5983. break;
  5984. case BfUnaryOp_InvertBits:
  5985. {
  5986. mResult.mIsLiteral = wasLiteral;
  5987. if (mResult.mType->IsInteger())
  5988. {
  5989. switch (mResult.mType->mSize)
  5990. {
  5991. case 1:
  5992. mResult.mUInt8 = ~mResult.mUInt8;
  5993. break;
  5994. case 2:
  5995. mResult.mUInt16 = ~mResult.mUInt16;
  5996. break;
  5997. case 4:
  5998. mResult.mUInt32 = ~mResult.mUInt32;
  5999. break;
  6000. case 8:
  6001. mResult.mUInt64 = ~mResult.mUInt64;
  6002. break;
  6003. }
  6004. }
  6005. }
  6006. break;
  6007. default:
  6008. Fail("Invalid operator for debug expression", opToken);
  6009. break;
  6010. }
  6011. if (numericFail)
  6012. {
  6013. Fail("Operator can only be used on numeric types", opToken);
  6014. mResult = DbgTypedValue();
  6015. }
  6016. }
  6017. void DbgExprEvaluator::Visit(BfUnaryOperatorExpression* unaryOpExpr)
  6018. {
  6019. PerformUnaryExpression(unaryOpExpr->mOpToken, unaryOpExpr->mOp, unaryOpExpr->mExpression);
  6020. }
  6021. bool DbgExprEvaluator::ResolveArgValues(const BfSizedArray<ASTREF(BfExpression*)>& arguments, SizedArrayImpl<DbgTypedValue>& outArgValues)
  6022. {
  6023. for (int argIdx = 0; argIdx < (int) arguments.size(); argIdx++)
  6024. {
  6025. //BfExprEvaluator exprEvaluator(mModule);
  6026. //exprEvaluator.Evaluate(arguments[argIdx]);
  6027. auto arg = arguments[argIdx];
  6028. DbgTypedValue argValue;
  6029. if (arg != NULL)
  6030. argValue = Resolve(arg);
  6031. if (argValue)
  6032. {
  6033. /*if (argValue.mType->IsRef())
  6034. {
  6035. argValue.mIsAddr = false;
  6036. }
  6037. else if (!argValue.mType->IsStruct())
  6038. argValue = mModule->LoadValue(argValue);*/
  6039. }
  6040. outArgValues.push_back(argValue);
  6041. }
  6042. return true;
  6043. }
  6044. DbgTypedValue DbgExprEvaluator::CreateCall(DbgSubprogram* method, DbgTypedValue thisVal, DbgTypedValue structRetVal, bool bypassVirtual, CPURegisters* registers)
  6045. {
  6046. // Why did we have the Not Runing thing for Exception? It means that when we crash we can't execute functions anymore.
  6047. // That doesn't seem good
  6048. /*if (mDebugger->mRunState == RunState_Exception)
  6049. {
  6050. mPassInstance->Fail("Not running");
  6051. return DbgTypedValue();
  6052. }*/
  6053. #ifdef BF_WANTS_LOG_DBGEXPR
  6054. auto _GetResultString = [&](DbgTypedValue val)
  6055. {
  6056. String result;
  6057. if (val.mSrcAddress != 0)
  6058. {
  6059. result += StrFormat("0x%p ", val.mSrcAddress);
  6060. int64 vals[4] = { 0 };
  6061. mDebugger->ReadMemory(val.mSrcAddress, 4 * 8, vals);
  6062. result += StrFormat("%lld %lld %lld %lld", vals[0], vals[1], vals[2], vals[3]);
  6063. }
  6064. else
  6065. {
  6066. result += StrFormat("%lld", val.mInt64);
  6067. }
  6068. return result;
  6069. };
  6070. #endif
  6071. int curCallResultIdx = mCallResultIdx++;
  6072. if (((mExpressionFlags & DwEvalExpressionFlag_AllowCalls) == 0) || (mCreatedPendingCall))
  6073. {
  6074. BfLogDbgExpr(" BlockedSideEffects\n");
  6075. mBlockedSideEffects = true;
  6076. return GetDefaultTypedValue(method->mReturnType);
  6077. }
  6078. mHadSideEffects = true;
  6079. // Our strategy is to create "pending results" for each call in a debug expression, and then we continually re-evaluate the
  6080. // entire expression using the actual returned results for each of those calls until we can finally evaluate it as a whole
  6081. if (curCallResultIdx < (int)mCallResults->size() - 1)
  6082. {
  6083. auto callResult = (*mCallResults)[curCallResultIdx];
  6084. auto result = callResult.mResult;
  6085. if (!callResult.mSRetData.IsEmpty())
  6086. {
  6087. result = structRetVal;
  6088. mDebugger->WriteMemory(result.mSrcAddress, &callResult.mSRetData[0], (int)callResult.mSRetData.size());
  6089. }
  6090. BfLogDbgExpr(" using cached results %s\n", _GetResultString(result).c_str());
  6091. return result;
  6092. }
  6093. else if (curCallResultIdx == (int)mCallResults->size() - 1)
  6094. {
  6095. auto& callResult = (*mCallResults)[curCallResultIdx];
  6096. CPURegisters newPhysRegisters;
  6097. mDebugger->PopulateRegisters(&newPhysRegisters);
  6098. DbgTypedValue returnVal;
  6099. if (method->mReturnType != 0)
  6100. {
  6101. if (callResult.mStructRetVal)
  6102. returnVal = callResult.mStructRetVal;
  6103. else
  6104. returnVal = mDebugger->ReadReturnValue(&newPhysRegisters, method->mReturnType);
  6105. bool hadRef = false;
  6106. auto returnType = method->mReturnType->RemoveModifiers(&hadRef);
  6107. if (hadRef)
  6108. {
  6109. returnVal = ReadTypedValue(NULL, returnType, returnVal.mPtr, DbgAddrType_Target);
  6110. returnVal.mType = returnType;
  6111. }
  6112. }
  6113. else
  6114. {
  6115. returnVal.mType = mDbgModule->GetPrimitiveType(DbgType_Void, GetLanguage());
  6116. }
  6117. BfLogDbgExpr(" using new results %s\n", _GetResultString(returnVal).c_str());
  6118. mDebugger->RestoreAllRegisters();
  6119. if ((method->mReturnType->IsCompositeType()) && (mDebugger->CheckNeedsSRetArgument(method->mReturnType)))
  6120. {
  6121. callResult.mSRetData.Resize(method->mReturnType->GetByteCount());
  6122. mDebugger->ReadMemory(returnVal.mSrcAddress, method->mReturnType->GetByteCount(), &callResult.mSRetData[0]);
  6123. }
  6124. callResult.mResult = returnVal;
  6125. return returnVal;
  6126. }
  6127. else
  6128. {
  6129. BfLogDbgExpr(" new call\n");
  6130. }
  6131. // It's a new call
  6132. addr_target startAddr = method->mBlock.mLowPC;
  6133. if ((method->mVTableLoc != -1) && (thisVal))
  6134. {
  6135. addr_target thisPtr;
  6136. bool isBfObject = false;
  6137. if (thisVal.mType->IsCompositeType())
  6138. {
  6139. isBfObject = thisVal.mType->IsBfObject();
  6140. thisPtr = thisVal.mSrcAddress;
  6141. }
  6142. else
  6143. {
  6144. isBfObject = thisVal.mType->IsBfObjectPtr();
  6145. thisPtr = thisVal.mPtr;
  6146. }
  6147. addr_target vtablePtr = mDebugger->ReadMemory<addr_target>(thisPtr);
  6148. if (isBfObject)
  6149. {
  6150. mDebugTarget->GetCompilerSettings();
  6151. if (mDebugTarget->mBfObjectHasFlags)
  6152. vtablePtr &= ~0xFF;
  6153. }
  6154. if (method->mVTableLoc >= 0x100000)
  6155. {
  6156. // Virtual ext method, double indirection
  6157. addr_target extAddr = mDebugger->ReadMemory<addr_target>(vtablePtr + (uint)((method->mVTableLoc>>20) - 1)*sizeof(addr_target));
  6158. startAddr = mDebugger->ReadMemory<addr_target>(extAddr + (uint)(method->mVTableLoc & 0xFFFFF)*sizeof(addr_target));
  6159. }
  6160. else
  6161. startAddr = mDebugger->ReadMemory<addr_target>(vtablePtr + method->mVTableLoc);
  6162. }
  6163. else
  6164. {
  6165. if ((startAddr == 0) && (method->mLinkName != NULL))
  6166. {
  6167. startAddr = mDebugTarget->FindSymbolAddr(method->mLinkName);
  6168. }
  6169. else if ((startAddr == 0) && (method->mName != NULL))
  6170. {
  6171. startAddr = mDebugTarget->FindSymbolAddr(method->mName);
  6172. }
  6173. }
  6174. if ((startAddr == (addr_target)0) || (startAddr == (addr_target)-1))
  6175. {
  6176. mPassInstance->Fail("Unable to find address for method, possibly due to compiler optimizations.");
  6177. return DbgTypedValue();
  6178. }
  6179. mDebugger->SaveAllRegisters();
  6180. BfLogDbg("Starting RunState_DebugEval on thread %d\n", mDebugger->mActiveThread->mThreadId);
  6181. addr_target prevSP = registers->GetSP();
  6182. //registers->mIntRegs.efl = 0x244;
  6183. //mDebugger->PushValue(registers, 0);
  6184. mDebugger->PushValue(registers, 42);
  6185. *(registers->GetPCRegisterRef()) = startAddr;
  6186. mDebugger->mDebugEvalSetRegisters = *registers;
  6187. // Set trap flag, which raises "single-step" exception
  6188. // If we step ONTO the PC we set, then that means we have returned from kernel mode
  6189. // so we need to set the registers again (they would have been clobbered due to SetThreadContext bugs).
  6190. // If we step past the PC then we're all good
  6191. registers->mIntRegs.efl |= 0x100;
  6192. mDebugger->SetRegisters(registers);
  6193. //::ResumeThread(mDebugger->mActiveThread->mHThread);
  6194. //TODO: For debugging stepping:
  6195. if ((mExpressionFlags & DwEvalExpressionFlag_StepIntoCalls) != 0)
  6196. {
  6197. mDebugger->mDebugManager->mOutMessages.push_back("rehupLoc");
  6198. return DbgTypedValue();
  6199. }
  6200. /*if (true)
  6201. {
  6202. return DbgTypedValue();
  6203. }*/
  6204. // mDebugger->mActiveThread->mIsAtBreakpointAddress = 0;
  6205. // mDebugger->mActiveThread->mBreakpointAddressContinuing = 0;
  6206. auto prevRunState = mDebugger->mRunState;
  6207. mDebugger->mRunState = RunState_DebugEval;
  6208. mDebugger->mExplicitStopThread = NULL;
  6209. mDebugger->mRequestedStackFrameIdx = -1;
  6210. BfLogDbg("DbgExprEvaluator::CreateCall %p in thread %d\n", startAddr, mDebugger->mActiveThread->mThreadId);
  6211. DbgCallResult callResult;
  6212. callResult.mSubProgram = method;
  6213. callResult.mStructRetVal = structRetVal;
  6214. mCallResults->push_back(callResult);
  6215. mCreatedPendingCall = true;
  6216. return GetDefaultTypedValue(method->mReturnType);
  6217. }
  6218. DbgTypedValue DbgExprEvaluator::CreateCall(BfAstNode* targetSrc, DbgTypedValue target, DbgSubprogram* method, bool bypassVirtual, const BfSizedArray<ASTREF(BfExpression*)>& arguments, SizedArrayImpl<DbgTypedValue>& argValues)
  6219. {
  6220. HashSet<String> splatParams;
  6221. SizedArray<DbgMethodArgument, 4> argPushQueue;
  6222. //
  6223. {
  6224. for (auto variable : method->mBlock.mVariables)
  6225. {
  6226. if ((variable->mName == NULL) && (variable->mName[0] != '$'))
  6227. continue;
  6228. const char* dollarPos = strchr(variable->mName + 1, '$');
  6229. if (dollarPos == NULL)
  6230. continue;
  6231. String varName = String(variable->mName + 1, dollarPos - variable->mName - 1);
  6232. splatParams.Add(varName);
  6233. }
  6234. }
  6235. int argIdx = 0;
  6236. int paramIdx = 0;
  6237. auto _PushArg = [&](const DbgTypedValue& typedValue, DbgVariable* param)
  6238. {
  6239. if (typedValue.mType->GetByteCount() == 0)
  6240. return;
  6241. if ((param != NULL) && (param->mType != NULL) && (param->mType->IsCompositeType()))
  6242. {
  6243. if ((param->mName != NULL) && (splatParams.Contains(param->mName)))
  6244. {
  6245. std::function<void(const DbgTypedValue& typedVal)> _SplatArgs = [&](const DbgTypedValue& typedVal)
  6246. {
  6247. auto type = typedVal.mType->RemoveModifiers();
  6248. type = type->GetPrimaryType();
  6249. if (type->IsValuelessType())
  6250. return;
  6251. if (!type->IsCompositeType())
  6252. {
  6253. auto elemTypedValue = ReadTypedValue(targetSrc, type, typedVal.mSrcAddress, DbgAddrType_Target);
  6254. DbgMethodArgument methodArg;
  6255. methodArg.mTypedValue = elemTypedValue;
  6256. argPushQueue.push_back(methodArg);
  6257. return;
  6258. }
  6259. auto baseType = type->GetBaseType();
  6260. if (baseType != NULL)
  6261. {
  6262. DbgTypedValue baseValue = typedVal;
  6263. baseValue.mType = baseType;
  6264. _SplatArgs(baseValue);
  6265. }
  6266. for (auto member : type->mMemberList)
  6267. {
  6268. if ((member->mIsStatic) || (member->mIsConst))
  6269. continue;
  6270. DbgTypedValue memberValue;
  6271. memberValue.mSrcAddress = typedVal.mSrcAddress + member->mMemberOffset;
  6272. memberValue.mType = member->mType;
  6273. _SplatArgs(memberValue);
  6274. }
  6275. };
  6276. _SplatArgs(typedValue);
  6277. return;
  6278. }
  6279. }
  6280. DbgMethodArgument methodArg;
  6281. methodArg.mTypedValue = typedValue;
  6282. methodArg.mWantsRef = param->mType->IsRef();
  6283. argPushQueue.push_back(methodArg);
  6284. };
  6285. bool thisByValue = false;
  6286. int methodParamCount = method->mParams.Size();
  6287. if (methodParamCount > 0)
  6288. {
  6289. method->mParams;
  6290. }
  6291. if (method->mHasThis)
  6292. {
  6293. auto param = method->mParams[paramIdx];
  6294. if ((param->mType != NULL) && (param->mType->IsValueType()))
  6295. thisByValue = true;
  6296. if (!target)
  6297. {
  6298. Fail(StrFormat("An object reference is required to invoke the non-static method '%s'", method->ToString().c_str()), targetSrc);
  6299. return DbgTypedValue();
  6300. }
  6301. _PushArg(target, param);
  6302. methodParamCount--;
  6303. }
  6304. else
  6305. {
  6306. if (target.mPtr != 0)
  6307. {
  6308. Fail(StrFormat("Method '%s' cannot be accessed with an instance reference; qualify it with a type name instead", method->ToString().c_str()), targetSrc);
  6309. return DbgTypedValue();
  6310. }
  6311. }
  6312. DbgTypedValue expandedParamsArray;
  6313. DbgType* expandedParamsElementType = NULL;
  6314. int extendedParamIdx = 0;
  6315. int paramOffset = method->mHasThis ? 1 : 0;
  6316. while (true)
  6317. {
  6318. if (paramIdx >= (int)method->mParams.Size() - paramOffset)
  6319. {
  6320. if (argIdx < (int)arguments.size())
  6321. {
  6322. int showArgIdx = (int)method->mParams.Size();
  6323. if (method->mHasThis)
  6324. showArgIdx--;
  6325. //WTF- what was this "Calling constructor" error about?!
  6326. /*if (methodInstance->mMethodDef->mMethodDeclaration != NULL)
  6327. mModule->mSystem->Warn(StrFormat("Trying to call constructor '%s'", mModule->MethodToString(methodInstance).c_str()), methodInstance->mMethodDef->GetRefNode());*/
  6328. Fail(StrFormat("Too many arguments. Expected %d fewer.", (int)arguments.size() - (methodParamCount)), arguments[showArgIdx]);
  6329. /*if (methodInstance->mMethodDef->mMethodDeclaration != NULL)
  6330. mModule->mCompiler->mPassInstance->MoreInfo(StrFormat("See method declaration"), methodInstance->mMethodDef->mMethodDeclaration);*/
  6331. return DbgTypedValue();
  6332. }
  6333. break;
  6334. }
  6335. DbgVariable* param = NULL;
  6336. DbgType* wantType = NULL;
  6337. if (expandedParamsElementType != NULL)
  6338. {
  6339. wantType = expandedParamsElementType;
  6340. }
  6341. else
  6342. {
  6343. param = method->mParams[paramIdx + paramOffset];
  6344. wantType = param->mType;
  6345. //TODO:
  6346. /*if (method->mParams[paramIdx]->mParamType == BfParamType_Params)
  6347. {
  6348. //TODO: Check to see if it's a direct array pass
  6349. bool isDirectPass = false;
  6350. if (argIdx < (int)arguments.size())
  6351. {
  6352. if (argValues[argIdx].mValue == NULL)
  6353. return DbgTypedValue();
  6354. if (mModule->CanCast(argValues[argIdx], wantType))
  6355. isDirectPass = true;
  6356. }
  6357. if (!isDirectPass)
  6358. {
  6359. BfArrayType* arrayType = (BfArrayType*) wantType;
  6360. if (arrayType->IsIncomplete())
  6361. mModule->PopulateType(arrayType, true);
  6362. expandedParamsElementType = arrayType->mTypeGenericArguments[0];
  6363. int arrayClassSize = arrayType->mInstSize - expandedParamsElementType->mSize;
  6364. int numElements = (int) arguments.size() - argIdx;
  6365. Value* sizeValue = mModule->GetConstValue(arrayClassSize);
  6366. Value* elementDataSize = mModule->mIRBuilder->CreateMul(mModule->GetConstValue(expandedParamsElementType->mSize), mModule->GetConstValue(numElements));
  6367. sizeValue = mModule->mIRBuilder->CreateAdd(sizeValue, elementDataSize);
  6368. auto paramsData = mModule->GetHeadIRBuilder()->CreateAlloca(Type::getInt8Ty(*mModule->mLLVMContext), sizeValue, "paramsData");
  6369. expandedParamsArray = DbgTypedValue(mModule->mIRBuilder->CreateBitCast(paramsData, arrayType->mLLVMType),
  6370. arrayType, false);
  6371. MatchConstructor(targetSrc, expandedParamsArray, arrayType, SizedArray<BfExpression*, 1>(), false);
  6372. //TODO: Assert 'length' var is at slot 1
  6373. auto arrayBits = mModule->mIRBuilder->CreateBitCast(expandedParamsArray.mValue, arrayType->mBaseType->mPtrLLVMType);
  6374. if ((arrayType->mBaseType->mFieldInstances.size() < 0) || (arrayType->mBaseType->mFieldInstances[0].GetFieldDef()->mName != "mLength"))
  6375. {
  6376. mModule->Fail("INTERNAL ERROR: Unable to find array 'length' field", targetSrc);
  6377. return DbgTypedValue();
  6378. }
  6379. auto addr = mModule->mIRBuilder->CreateConstInBoundsGEP2_32(arrayBits, 0, 1, "length");
  6380. mModule->mIRBuilder->CreateStore(mModule->GetConstValue(numElements), addr);
  6381. llvmArgs.push_back(expandedParamsArray.mValue);
  6382. continue;
  6383. }
  6384. }*/
  6385. }
  6386. BfExpression* arg = NULL;
  6387. DbgTypedValue argValue;
  6388. if (argIdx < (int) arguments.size())
  6389. {
  6390. arg = arguments[argIdx];
  6391. argValue = argValues[argIdx];
  6392. }
  6393. else if (param->mIsConst)
  6394. {
  6395. argValue.mType = param->mType;
  6396. argValue.mInt64 = param->mConstValue;
  6397. }
  6398. else if (mPassInstance != NULL)
  6399. {
  6400. if (expandedParamsArray)
  6401. break;
  6402. //TODO: Default values
  6403. /*if ((argIdx >= (int) methodInstance->mDefaultValues.size()) || (methodInstance->mDefaultValues[argIdx] == NULL))
  6404. {
  6405. BfAstNode* refNode = targetSrc;
  6406. if (arguments.size() > 0)
  6407. refNode = arguments.back();
  6408. mModule->Fail(StrFormat("Not enough parameters specified. Got %d, expected %d.", arguments.size(), methodInstance->mParamTypes.size()), refNode);
  6409. return DbgTypedValue();
  6410. }
  6411. llvmArgs.push_back(methodInstance->mDefaultValues[argIdx]);*/
  6412. BfAstNode* refNode = targetSrc;
  6413. if (arguments.size() > 0)
  6414. refNode = arguments.back();
  6415. Fail(StrFormat("Not enough parameters specified. Expected %d more.", methodParamCount - (int)arguments.size()), refNode);
  6416. return DbgTypedValue();
  6417. argIdx++;
  6418. paramIdx++;
  6419. continue;
  6420. }
  6421. if (argValue.mType == NULL)
  6422. return DbgTypedValue();
  6423. if (arg != NULL)
  6424. {
  6425. /*if (wantType->IsGenericParam())
  6426. {
  6427. auto genericParamType = (BfGenericParamType*) wantType;
  6428. if (genericParamType->mGenericParamKind == BfGenericParamKind_Method)
  6429. wantType = moduleMethodInstance.mMethodInstance->mMethodGenericArguments[genericParamType->mGenericParamIdx];
  6430. }*/
  6431. if ((wantType->mTypeCode == DbgType_Struct) ||
  6432. (wantType->mTypeCode == DbgType_Class) ||
  6433. (wantType->mTypeCode == DbgType_Union))
  6434. {
  6435. if (GetLanguage() != DbgLanguage_Beef)
  6436. {
  6437. Fail(StrFormat("Calling methods that take structs, classes, or unions by value is not supported"), arg);
  6438. return DbgTypedValue();
  6439. }
  6440. }
  6441. if (wantType->IsRef())
  6442. wantType = wantType->mTypeParam;
  6443. /*{
  6444. if (argValue.mSrcAddress == 0)
  6445. {
  6446. Fail(StrFormat("Unable to get address of argument %s", method->GetParamName(paramIdx).c_str()), arg);
  6447. return DbgTypedValue();
  6448. }
  6449. wantType = mDbgModule->GetPointerType(wantType->mTypeParam);
  6450. argValue.mPtr = argValue.mSrcAddress;
  6451. argValue.mSrcAddress = 0;
  6452. argValue.mType = wantType;
  6453. }*/
  6454. argValue = Cast(arg, argValue, wantType);
  6455. if (!argValue)
  6456. return DbgTypedValue();
  6457. /*if (wantType->IsStruct())
  6458. {
  6459. // We need to make a temp and get the addr of that
  6460. if (!argValue.mIsAddr)
  6461. {
  6462. auto tempVar = mModule->GetHeadIRBuilder()->CreateAlloca(argValue.mType->mLLVMType, NULL, "agg.tmp");
  6463. int align = argValue.mType->mAlign;
  6464. tempVar->setAlignment(align);
  6465. mModule->mIRBuilder->CreateStore(argValue.mValue, tempVar);
  6466. //mModule->mIRBuilder->CreateMemCpy(tempVar, argValue.mValue, mModule->GetConstValue(argValue.mType->mDataSize), align, argValue.mType->IsVolatile());
  6467. argValue = DbgTypedValue(tempVar, argValue.mType, true);
  6468. }
  6469. }
  6470. else if (!wantType->IsRef())
  6471. argValue = mModule->LoadValue(argValue);*/
  6472. }
  6473. if (!argValue)
  6474. {
  6475. Fail("Invalid expression type", arg);
  6476. return DbgTypedValue();
  6477. }
  6478. //TODO:
  6479. /*if (expandedParamsArray)
  6480. {
  6481. auto firstAddr = mModule->mIRBuilder->CreateConstInBoundsGEP2_32(expandedParamsArray.mValue, 0, 1);
  6482. auto indexedAddr = mModule->mIRBuilder->CreateConstInBoundsGEP1_32(firstAddr, extendedParamIdx);
  6483. mModule->mIRBuilder->CreateStore(argValue.mValue, indexedAddr);
  6484. extendedParamIdx++;
  6485. }
  6486. else*/
  6487. {
  6488. //llvmArgs.push_back(argValue.mValue);
  6489. _PushArg(argValue, param);
  6490. paramIdx++;
  6491. }
  6492. argIdx++;
  6493. }
  6494. return CreateCall(method, argPushQueue, bypassVirtual);
  6495. }
  6496. DbgTypedValue DbgExprEvaluator::CreateCall(DbgSubprogram* method, SizedArrayImpl<DbgMethodArgument>& argPushQueue, bool bypassVirtual)
  6497. {
  6498. BfLogDbgExpr("CreateCall #%d %s", mCallResultIdx, method->mName);
  6499. if (mDebugger->IsMiniDumpDebugger())
  6500. {
  6501. Fail("Cannot call functions in a minidump", NULL);
  6502. return GetDefaultTypedValue(method->mReturnType);
  6503. }
  6504. if ((mExpressionFlags & DwEvalExpressionFlag_AllowCalls) == 0)
  6505. {
  6506. mBlockedSideEffects = true;
  6507. return GetDefaultTypedValue(method->mReturnType);
  6508. }
  6509. mHadSideEffects = true;
  6510. // We need current physical registers to make sure we push params in correct stack frame
  6511. CPURegisters registers;
  6512. bool canSetRegisters = mDebugger->PopulateRegisters(&registers);
  6513. auto* regSP = registers.GetSPRegisterRef();
  6514. if (mCallStackPreservePos != 0)
  6515. {
  6516. if (mCallStackPreservePos <= *regSP)
  6517. *regSP = mCallStackPreservePos;
  6518. }
  6519. int paramIdx = argPushQueue.size() - 1;
  6520. if (method->mHasThis)
  6521. paramIdx--;
  6522. bool thisByValue = false;
  6523. if ((method->mHasThis) && (!method->mParams.IsEmpty()))
  6524. {
  6525. auto param = method->mParams[0];
  6526. if ((param->mType != NULL) && (param->mType->IsValueType()))
  6527. thisByValue = true;
  6528. }
  6529. DbgTypedValue structRetVal;
  6530. if (mDebugger->CheckNeedsSRetArgument(method->mReturnType))
  6531. {
  6532. int retSize = BF_ALIGN(method->mReturnType->GetByteCount(), 16);
  6533. *regSP -= retSize;
  6534. structRetVal.mType = method->mReturnType;
  6535. structRetVal.mSrcAddress = *regSP;
  6536. // For chained calls we need to leave the sret form the previous calls intact
  6537. mCallStackPreservePos = *regSP;
  6538. }
  6539. for (int i = (int)argPushQueue.size() - 1; i >= 0; i--)
  6540. {
  6541. auto& arg = argPushQueue[i];
  6542. // If we have something like an int constant when we need to pass by int&, then we need to allocate
  6543. // on the stack and pass that address
  6544. if (arg.mWantsRef)
  6545. {
  6546. auto& typedValue = arg.mTypedValue;
  6547. auto rootType = typedValue.mType->RemoveModifiers();
  6548. if (arg.mTypedValue.mSrcAddress != 0)
  6549. {
  6550. typedValue.mPtr = typedValue.mSrcAddress;
  6551. }
  6552. else
  6553. {
  6554. int rootSize = rootType->GetByteCount();
  6555. *regSP -= BF_ALIGN(rootSize, 16);
  6556. mDebugger->WriteMemory(*regSP, &arg.mTypedValue.mInt64, rootSize); // Write from debugger memory to target
  6557. typedValue.mPtr = *regSP;
  6558. }
  6559. typedValue.mType = mDbgModule->GetPointerType(rootType);
  6560. typedValue.mSrcAddress = 0;
  6561. }
  6562. }
  6563. if (structRetVal.mSrcAddress != 0)
  6564. {
  6565. BfLogDbgExpr(" SRet:0x%p", structRetVal.mSrcAddress);
  6566. mDebugger->AddParamValue(0, method->mHasThis && !thisByValue, &registers, structRetVal);
  6567. paramIdx++;
  6568. }
  6569. DbgTypedValue thisVal;
  6570. for (int padCount = 0; true; padCount++)
  6571. {
  6572. auto regSave = registers;
  6573. int paramIdxSave = paramIdx;
  6574. *regSP -= padCount * sizeof(addr_target);
  6575. for (int i = (int)argPushQueue.size() - 1; i >= 0; i--)
  6576. {
  6577. auto& arg = argPushQueue[i];
  6578. if ((i == 0) && (method->mHasThis) && (!method->ThisIsSplat()))
  6579. {
  6580. thisVal = arg.mTypedValue;
  6581. addr_target thisAddr;
  6582. if (thisVal.mType->IsCompositeType())
  6583. thisAddr = thisVal.mSrcAddress;
  6584. else
  6585. thisAddr = thisVal.mPtr;
  6586. mDebugger->SetThisRegister(&registers, thisAddr);
  6587. if (padCount == 0)
  6588. BfLogDbgExpr(" This:0x%p", thisAddr);
  6589. }
  6590. else
  6591. {
  6592. mDebugger->AddParamValue(paramIdx, method->mHasThis, &registers, arg.mTypedValue);
  6593. paramIdx--;
  6594. }
  6595. }
  6596. #ifdef BF_DBG_64
  6597. // Stack must be 16-byte aligned
  6598. if ((*regSP & 0xF) == 0)
  6599. break;
  6600. #else
  6601. break;
  6602. #endif
  6603. registers = regSave;
  6604. paramIdx = paramIdxSave;
  6605. BF_ASSERT(padCount < 3);
  6606. }
  6607. return CreateCall(method, thisVal, structRetVal, bypassVirtual, &registers);
  6608. }
  6609. DbgTypedValue DbgExprEvaluator::MatchMethod(BfAstNode* targetSrc, DbgTypedValue target, bool allowImplicitThis, bool bypassVirtual, const StringImpl& methodName,
  6610. const BfSizedArray<ASTREF(BfExpression*)>& arguments, BfSizedArray<ASTREF(BfAstNode*)>* methodGenericArguments)
  6611. {
  6612. SetAndRestoreValue<String*> prevReferenceId(mReferenceId, NULL);
  6613. bool wantCtor = methodName.IsEmpty();
  6614. mDbgModule->ParseGlobalsData();
  6615. //mDbgModule->ParseSymbolData();
  6616. SizedArray<DbgTypedValue, 4> argValues;
  6617. if (!ResolveArgValues(arguments, argValues))
  6618. return DbgTypedValue();
  6619. if ((methodName == "__cast") || (methodName == "__bitcast"))
  6620. {
  6621. if (argValues.size() > 0)
  6622. {
  6623. String typeName = "";
  6624. for (int argIdx = 0; argIdx < (int)argValues.size() - 1; argIdx++)
  6625. {
  6626. auto arg = argValues[argIdx];
  6627. if (!arg)
  6628. return DbgTypedValue();
  6629. if ((arg.mType->IsPointer()) && ((arg.mType->mTypeParam->mTypeCode == DbgType_UChar) || (arg.mType->mTypeParam->mTypeCode == DbgType_SChar)))
  6630. {
  6631. typeName += arg.mCharPtr;
  6632. }
  6633. else if ((arg.mType->mTypeCode == DbgType_i32) || (arg.mType->mTypeCode == DbgType_i64))
  6634. {
  6635. if (typeName.IsEmpty())
  6636. {
  6637. // Fake this int as a type pointer
  6638. arg.mSrcAddress = arg.mUInt64;
  6639. BeefTypeToString(arg, typeName);
  6640. }
  6641. else
  6642. typeName += BfTypeUtils::HashEncode64(arg.mInt64);
  6643. }
  6644. else
  6645. {
  6646. BeefTypeToString(arg, typeName);
  6647. }
  6648. }
  6649. auto castedType = mDbgModule->FindType(typeName, NULL, GetLanguage(), true);
  6650. if (castedType == NULL)
  6651. {
  6652. if (typeName.EndsWith('*'))
  6653. {
  6654. auto noPtrTypeEntry = mDbgModule->FindType(typeName.Substring(0, typeName.length() - 1), NULL, DbgLanguage_Beef, true);
  6655. if (noPtrTypeEntry != NULL)
  6656. castedType = mDbgModule->GetPointerType(noPtrTypeEntry);
  6657. }
  6658. }
  6659. int targetArgIdx = argValues.size() - 1;
  6660. if (castedType == NULL)
  6661. {
  6662. Fail(StrFormat("Unable to find type: '%s'", typeName.c_str()), targetSrc);
  6663. return argValues[targetArgIdx];
  6664. }
  6665. if (methodName == "__bitcast")
  6666. {
  6667. DbgTypedValue result = argValues[targetArgIdx];
  6668. result.mType = castedType;
  6669. return result;
  6670. }
  6671. return Cast(arguments[targetArgIdx], argValues[targetArgIdx], castedType, true);
  6672. }
  6673. }
  6674. else if (methodName == "__hasField")
  6675. {
  6676. if (argValues.size() == 2)
  6677. {
  6678. auto checkType = argValues[0].mType;
  6679. if ((checkType != NULL) && (checkType->IsPointer()))
  6680. checkType = checkType->mTypeParam;
  6681. if (checkType != NULL)
  6682. {
  6683. //TODO: Protect
  6684. String findFieldName = argValues[1].mCharPtr;
  6685. DbgTypedValue result;
  6686. result.mType = mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage());
  6687. result.mBool = HasField(checkType, findFieldName);
  6688. return result;
  6689. }
  6690. }
  6691. }
  6692. else if (methodName == "__desc")
  6693. {
  6694. if (argValues.size() == 1)
  6695. {
  6696. auto checkType = argValues[0].mType;
  6697. if ((checkType != NULL) && (checkType->IsPointer()))
  6698. checkType = checkType->mTypeParam;
  6699. if (checkType != NULL)
  6700. {
  6701. checkType = checkType->GetPrimaryType();
  6702. String dsc = "DESCRIPTION OF ";
  6703. dsc += checkType->ToString();
  6704. dsc += "\n";
  6705. dsc += "From Compile Unit: ";
  6706. dsc += checkType->mCompileUnit->mName;
  6707. dsc += "\n";
  6708. dsc += StrFormat("Size: %d\n", checkType->GetByteCount());
  6709. dsc += StrFormat("Align: %d\n", checkType->GetAlign());
  6710. for (auto member : checkType->mMemberList)
  6711. {
  6712. dsc += " ";
  6713. if (member->mIsConst)
  6714. dsc += "const ";
  6715. if (member->mIsExtern)
  6716. dsc += "extern ";
  6717. if (member->mIsStatic)
  6718. dsc += "static ";
  6719. dsc += member->mType->ToString();
  6720. dsc += " ";
  6721. dsc += member->mName;
  6722. if (!member->mIsStatic)
  6723. {
  6724. dsc += StrFormat(" Offset:%d", member->mMemberOffset);
  6725. }
  6726. dsc += StrFormat(" Size:%d", member->mType->GetByteCount());
  6727. if (member->mLinkName != NULL)
  6728. dsc += member->mLinkName;
  6729. dsc += "\n";
  6730. }
  6731. if ((mExpressionFlags & DwEvalExpressionFlag_AllowCalls) != 0)
  6732. mDebugger->OutputMessage(dsc);
  6733. return DbgTypedValue();
  6734. }
  6735. }
  6736. }
  6737. else if (methodName == "__demangleMethod")
  6738. {
  6739. if (argValues.size() == 2)
  6740. {
  6741. auto checkType = argValues[0].mType;
  6742. if (checkType->IsPointer())
  6743. checkType = checkType->mTypeParam;
  6744. //TODO: Protect
  6745. String findMethodName = argValues[1].mCharPtr;
  6746. checkType->PopulateType();
  6747. for (auto checkMethod : checkType->mMethodList)
  6748. {
  6749. if (checkMethod->mName == findMethodName)
  6750. {
  6751. static String demangledName;
  6752. demangledName = BfDemangler::Demangle(checkMethod->mLinkName, checkType->GetLanguage());
  6753. DbgTypedValue result;
  6754. result.mType = argValues[1].mType;
  6755. result.mCharPtr = demangledName.c_str();
  6756. result.mIsLiteral = true;
  6757. return result;
  6758. }
  6759. }
  6760. }
  6761. }
  6762. else if (methodName == "__demangle")
  6763. {
  6764. if (argValues.size() == 1)
  6765. {
  6766. auto rawTextType = mDbgModule->GetPrimitiveType(DbgType_RawText, GetLanguage());
  6767. String mangledName = argValues[0].mCharPtr;
  6768. static String demangledName;
  6769. demangledName = BfDemangler::Demangle(mangledName, DbgLanguage_Unknown);
  6770. if (demangledName.StartsWith("bf."))
  6771. demangledName.Remove(0, 3);
  6772. DbgTypedValue result;
  6773. result.mType = rawTextType;
  6774. result.mCharPtr = demangledName.c_str();
  6775. result.mIsLiteral = true;
  6776. return result;
  6777. }
  6778. }
  6779. else if (methodName == "__demangleFakeMember")
  6780. {
  6781. if (argValues.size() == 1)
  6782. {
  6783. auto checkType = argValues[0].mType;
  6784. if (checkType->IsPointer())
  6785. checkType = checkType->mTypeParam;
  6786. auto rawTextType = mDbgModule->GetPrimitiveType(DbgType_RawText, GetLanguage());
  6787. checkType->PopulateType();
  6788. auto firstMember = checkType->mMemberList.mHead;
  6789. static String demangledName;
  6790. demangledName = BfDemangler::Demangle(firstMember->mName, checkType->GetLanguage());
  6791. if (demangledName.StartsWith("bf."))
  6792. demangledName.Remove(0, 3);
  6793. DbgTypedValue result;
  6794. result.mType = rawTextType;
  6795. result.mCharPtr = demangledName.c_str();
  6796. result.mIsLiteral = true;
  6797. return result;
  6798. }
  6799. }
  6800. else if (methodName == "__funcName")
  6801. {
  6802. if (argValues.size() == 1)
  6803. {
  6804. auto funcPtr = argValues[0].mPtr;
  6805. String symbolName;
  6806. addr_target offset;
  6807. DbgModule* dwarf;
  6808. static String demangledName;
  6809. auto subProgram = mDebugTarget->FindSubProgram(funcPtr);
  6810. if (subProgram != NULL)
  6811. {
  6812. demangledName = subProgram->ToString();
  6813. }
  6814. else if (mDebugTarget->FindSymbolAt(funcPtr, &symbolName, &offset, &dwarf))
  6815. {
  6816. demangledName = BfDemangler::Demangle(symbolName, GetLanguage());
  6817. }
  6818. else
  6819. {
  6820. demangledName = StrFormat("0x%@", funcPtr);
  6821. }
  6822. DbgTypedValue result;
  6823. result.mType = mDbgModule->GetPrimitiveType(DbgType_Subroutine, GetLanguage());
  6824. result.mCharPtr = demangledName.c_str();
  6825. return result;
  6826. }
  6827. }
  6828. else if (methodName == "__funcTarget")
  6829. {
  6830. if (argValues.size() == 2)
  6831. {
  6832. auto funcPtr = argValues[0].mPtr;
  6833. auto funcTarget = argValues[1].mPtr;
  6834. String symbolName;
  6835. addr_target offset;
  6836. DbgModule* dwarf;
  6837. if (mDebugTarget->FindSymbolAt(funcPtr, &symbolName, &offset, &dwarf))
  6838. {
  6839. String firstParamType = BfDemangler::Demangle(symbolName, GetLanguage(), BfDemangler::Flag_CaptureTargetType);
  6840. auto targetType = mDbgModule->FindType(firstParamType, NULL, DbgLanguage_BeefUnfixed);
  6841. if (targetType)
  6842. {
  6843. if (!targetType->IsPointer())
  6844. targetType = mDbgModule->GetPointerType(targetType);
  6845. DbgTypedValue result;
  6846. result.mType = targetType;
  6847. result.mPtr = funcTarget;
  6848. return result;
  6849. }
  6850. }
  6851. return argValues[1];
  6852. }
  6853. }
  6854. else if (methodName == "__stringView")
  6855. {
  6856. if (argValues.size() >= 2)
  6857. {
  6858. if ((argValues[1].mType != NULL) && (argValues[1].mType->IsInteger()))
  6859. mCountResultOverride = (intptr)argValues[1].GetInt64();
  6860. return argValues[0];
  6861. }
  6862. }
  6863. else if (methodName == "__getHighBits")
  6864. {
  6865. if ((argValues.size() == 2) && (argValues[0]) && (argValues[1]))
  6866. {
  6867. uint64 val = argValues[0].mUInt64;
  6868. int bitCount = (int)argValues[1].GetInt64();
  6869. DbgTypedValue result;
  6870. result.mType = argValues[0].mType;
  6871. result.mInt64 = val >> (argValues[0].mType->GetByteCount() * 8 - bitCount);
  6872. return result;
  6873. }
  6874. }
  6875. else if (methodName == "__clearHighBits")
  6876. {
  6877. if ((argValues.size() == 2) && (argValues[0]) && (argValues[1]))
  6878. {
  6879. uint64 val = argValues[0].mUInt64;
  6880. int bitCount = (int)argValues[1].GetInt64();
  6881. if (bitCount <= 0)
  6882. return argValues[0];
  6883. int64 andBits = (0x8000000000000000LL) >> ((argValues[0].mType->GetByteCount() - 8) * 8 + bitCount - 1);
  6884. DbgTypedValue result;
  6885. result.mType = argValues[0].mType;
  6886. result.mInt64 = val & ~andBits;
  6887. return result;
  6888. }
  6889. }
  6890. else if (methodName == "__parseCompileUnits")
  6891. {
  6892. for (auto dbgModule : mDebugTarget->mDbgModules)
  6893. {
  6894. dbgModule->ParseCompileUnits();
  6895. }
  6896. }
  6897. DbgType* curTypeDef;
  6898. DbgType* targetTypeInst = NULL;
  6899. bool checkNonStatic = true;
  6900. if (target)
  6901. {
  6902. targetTypeInst = target.mType;
  6903. curTypeDef = targetTypeInst;
  6904. }
  6905. else if (target.mType) // Static targeted
  6906. {
  6907. if (target.mType->IsPrimitiveType())
  6908. {
  6909. //TODO ;
  6910. //targetTypeInst = mModule->GetPrimitiveStructType(target.mType);
  6911. }
  6912. else
  6913. targetTypeInst = target.mType;
  6914. if (targetTypeInst == NULL)
  6915. {
  6916. Fail("No static methods available", targetSrc);
  6917. return DbgTypedValue();
  6918. }
  6919. curTypeDef = targetTypeInst;
  6920. checkNonStatic = false;
  6921. }
  6922. else // Current scope
  6923. {
  6924. curTypeDef = GetCurrentType();
  6925. targetTypeInst = GetCurrentType();
  6926. auto currentMethod = GetCurrentMethod();
  6927. checkNonStatic = (currentMethod != NULL) && (currentMethod->mHasThis);
  6928. }
  6929. DbgSubprogram* methodDef = NULL;
  6930. BfTypeVector checkMethodGenericArguments;
  6931. bool isFailurePass = false;
  6932. DbgType* curTypeInst = targetTypeInst;
  6933. DwMethodMatcher methodMatcher(targetSrc, this, methodName, argValues, methodGenericArguments);
  6934. if (targetTypeInst != NULL)
  6935. methodMatcher.mTargetIsConst = targetTypeInst->IsConst();
  6936. if (targetTypeInst != NULL)
  6937. {
  6938. methodMatcher.CheckType(targetTypeInst, false);
  6939. if (methodMatcher.mBestMethodDef == NULL)
  6940. {
  6941. isFailurePass = true;
  6942. methodMatcher.CheckType(targetTypeInst, true);
  6943. }
  6944. }
  6945. if (methodMatcher.mBestMethodDef != NULL)
  6946. {
  6947. //methodGenericArguments = methodMatcher.mBestMethodGenericArguments;
  6948. curTypeInst = methodMatcher.mBestMethodTypeInstance;
  6949. methodDef = methodMatcher.mBestMethodDef;
  6950. }
  6951. if ((methodDef) && (methodDef->mHasThis) && (!target) && (allowImplicitThis))
  6952. {
  6953. target = GetThis();
  6954. /*if (!target)
  6955. {
  6956. mModule->Fail("Target required for non-static method", targetSrc);
  6957. return DbgTypedValue();
  6958. }*/
  6959. }
  6960. // Fail, check for delegate invocation
  6961. if (methodDef == NULL)
  6962. {
  6963. DbgTypedValue fieldVal;
  6964. if (allowImplicitThis)
  6965. {
  6966. //auto thisValue = mModule->GetThis();
  6967. //LookupField(targetSrc, thisValue, methodName);
  6968. fieldVal = LookupIdentifier(BfNodeDynCast<BfIdentifierNode>(targetSrc));
  6969. }
  6970. else
  6971. {
  6972. fieldVal = LookupField(targetSrc, target, methodName);
  6973. }
  6974. //TODO:
  6975. /*if (mPropDef != NULL)
  6976. fieldVal = GetResult();*/
  6977. /*if (fieldVal)
  6978. {
  6979. if (fieldVal.mType->IsTypeInstance())
  6980. {
  6981. auto fieldTypeInst = fieldVal.mType->ToTypeInstance();
  6982. if (fieldTypeInst->mTypeDef->mIsDelegate)
  6983. return MatchMethod(targetSrc, fieldVal, false, false, "Invoke", arguments, methodGenericArguments);
  6984. }
  6985. fieldVal.mType = mModule->ResolveGenericParam(fieldVal.mType);
  6986. if (fieldVal.mType->IsVar())
  6987. return DbgTypedValue(mModule->GetDefaultValue(fieldVal.mType), fieldVal.mType);
  6988. mModule->Fail(StrFormat("Cannot perform invocation on type '%s'", mModule->TypeToString(fieldVal.mType).c_str()), targetSrc);
  6989. return DbgTypedValue();
  6990. }*/
  6991. }
  6992. /*if ((!methodDef) && (!target))
  6993. {
  6994. String checkTypeName = methodName;
  6995. int wantNumGenericArgs = 0;
  6996. if ((methodGenericArguments != NULL) && (methodGenericArguments->size() > 0))
  6997. wantNumGenericArgs = (int)methodGenericArguments->size();
  6998. auto typeDef = mModule->mSystem->FindTypeDef(checkTypeName, wantNumGenericArgs, mModule->mCurTypeInstance->mTypeDef->mNamespaceSearch);
  6999. if (typeDef != NULL)
  7000. {
  7001. BfTypeVector genericArgs;
  7002. if (methodGenericArguments != NULL)
  7003. {
  7004. for (auto genericArg : *methodGenericArguments)
  7005. {
  7006. auto typeDef = mModule->ResolveTypeRef(genericArg);
  7007. if (typeDef == NULL)
  7008. return DbgTypedValue();
  7009. genericArgs.push_back(typeDef);
  7010. }
  7011. }
  7012. auto resolvedType = mModule->ResolveTypeDef(typeDef, genericArgs)->ToTypeInstance();
  7013. if (resolvedType != NULL)
  7014. {
  7015. if (!resolvedType->IsStruct())
  7016. {
  7017. mModule->Fail("Objects must be allocated through 'new' or 'stack'", targetSrc);
  7018. return DbgTypedValue();
  7019. }
  7020. DbgTypedValue structInst = DbgTypedValue(mModule->mIRBuilder->CreateAlloca(resolvedType->mLLVMType),
  7021. resolvedType, false);
  7022. MatchConstructor(targetSrc, structInst, resolvedType, arguments, false);
  7023. return DbgTypedValue(mModule->mIRBuilder->CreateLoad(structInst.mValue), resolvedType, false);
  7024. }
  7025. }
  7026. }*/
  7027. if ((methodDef == NULL) && (!target))
  7028. {
  7029. for (int compileUnitIdx = 0; compileUnitIdx < (int)mDbgModule->mCompileUnits.size(); compileUnitIdx++)
  7030. {
  7031. auto compileUnit = mDbgModule->mCompileUnits[compileUnitIdx];
  7032. methodMatcher.CheckType(compileUnit->mGlobalType, isFailurePass);
  7033. if (methodMatcher.mBestMethodDef != NULL)
  7034. {
  7035. isFailurePass = false;
  7036. curTypeInst = methodMatcher.mBestMethodTypeInstance;
  7037. methodDef = methodMatcher.mBestMethodDef;
  7038. break;
  7039. }
  7040. }
  7041. }
  7042. if ((methodDef == NULL) && ((methodGenericArguments == NULL) || (methodGenericArguments->IsEmpty())))
  7043. {
  7044. DbgTypedValue enumResult;
  7045. DbgType* enumType = target.mType;
  7046. if ((enumType != NULL) && (enumType->IsBfPayloadEnum()))
  7047. {
  7048. enumResult = CheckEnumCreation(targetSrc, enumType, methodName, arguments);
  7049. if (enumResult)
  7050. return enumResult;
  7051. }
  7052. }
  7053. if (methodDef == NULL)
  7054. {
  7055. Fail("Method does not exist", targetSrc);
  7056. return DbgTypedValue();
  7057. }
  7058. // Don't execute the method if we've had a failure (like an ambiguous lookup)
  7059. if ((mPassInstance != NULL) && (mPassInstance->HasFailed()))
  7060. return DbgTypedValue();
  7061. DbgTypedValue callTarget;
  7062. if (targetTypeInst == curTypeInst)
  7063. {
  7064. callTarget = target;
  7065. }
  7066. else if (target)
  7067. {
  7068. bool handled = false;
  7069. if (target.mType->IsCompositeType())
  7070. {
  7071. //BF_FATAL("Not implemented");
  7072. callTarget = target;
  7073. /*if (curTypeInst->IsObject())
  7074. {
  7075. // Box it
  7076. callTarget = mModule->Cast(targetSrc, target, curTypeInst, true);
  7077. handled = true;
  7078. }*/
  7079. }
  7080. /*else
  7081. target = mModule->LoadValue(target);*/
  7082. if (!handled)
  7083. {
  7084. /*Value* targetValue = target.mValue;
  7085. callTarget = DbgTypedValue(mModule->mIRBuilder->CreateBitCast(targetValue, curTypeInst->mPtrLLVMType), curTypeInst);*/
  7086. callTarget = target;
  7087. }
  7088. }
  7089. if (prevReferenceId.mPrevVal != NULL)
  7090. {
  7091. if (prevReferenceId.mPrevVal->IsEmpty())
  7092. *prevReferenceId.mPrevVal += ".";
  7093. *prevReferenceId.mPrevVal += methodDef->ToString();
  7094. }
  7095. return CreateCall(targetSrc, callTarget, methodDef, bypassVirtual, arguments, argValues);
  7096. }
  7097. void DbgExprEvaluator::DoInvocation(BfAstNode* target, BfSizedArray<ASTREF(BfExpression*)>& args, BfSizedArray<ASTREF(BfAstNode*)>* methodGenericArguments)
  7098. {
  7099. bool allowImplicitThis = false;
  7100. BfAstNode* methodNodeSrc = target;
  7101. bool bypassVirtual = false;
  7102. String targetFunctionName;
  7103. DbgTypedValue thisValue;
  7104. //TODO: This may just be a fully qualified static method name, so let's check that also
  7105. if (auto memberRefExpression = BfNodeDynCast<BfMemberReferenceExpression>(target))
  7106. {
  7107. //GetAutoComplete()->CheckMemberReference(memberRefExpression->mTarget, memberRefExpression->mDotToken, memberRefExpression->mMemberName);
  7108. if (memberRefExpression->mMemberName == NULL)
  7109. return;
  7110. if (memberRefExpression->IsA<BfBaseExpression>())
  7111. bypassVirtual = true;
  7112. methodNodeSrc = memberRefExpression->mMemberName;
  7113. if (auto attrIdentifier = BfNodeDynCast<BfAttributedIdentifierNode>(memberRefExpression->mMemberName))
  7114. {
  7115. methodNodeSrc = attrIdentifier->mIdentifier;
  7116. if (attrIdentifier->mIdentifier != NULL)
  7117. targetFunctionName = attrIdentifier->mIdentifier->ToString();
  7118. }
  7119. else
  7120. targetFunctionName = memberRefExpression->mMemberName->ToString();
  7121. if (memberRefExpression->mTarget == NULL)
  7122. {
  7123. // Dot-qualified
  7124. if ((mExpectingType != NULL) && (mExpectingType->IsStruct()))
  7125. {
  7126. mResult = DbgTypedValue();
  7127. mResult.mType = mExpectingType;
  7128. }
  7129. else
  7130. Fail("Unqualified dot syntax can only be used when the result type can be inferred", memberRefExpression->mDotToken);
  7131. }
  7132. else if (auto typeRef = BfNodeDynCast<BfTypeReference>(memberRefExpression->mTarget))
  7133. {
  7134. // Static method
  7135. mResult = DbgTypedValue();
  7136. mResult.mType = ResolveTypeRef(typeRef);
  7137. }
  7138. else
  7139. VisitChild(memberRefExpression->mTarget);
  7140. GetResult();
  7141. if (mResult.mType == NULL)
  7142. return;
  7143. thisValue = mResult;
  7144. mResult = DbgTypedValue();
  7145. }
  7146. else if (auto qualifiedName = BfNodeDynCast<BfQualifiedNameNode>(target))
  7147. {
  7148. /*if (GetAutoComplete() != NULL)
  7149. GetAutoComplete()->CheckMemberReference(qualifiedName->mLeft, qualifiedName->mDot, qualifiedName->mRight);*/
  7150. String leftName = qualifiedName->mLeft->ToString();
  7151. if (leftName == "base")
  7152. bypassVirtual = true;
  7153. methodNodeSrc = qualifiedName->mRight;
  7154. if (auto attrIdentifier = BfNodeDynCast<BfAttributedIdentifierNode>(qualifiedName->mRight))
  7155. {
  7156. methodNodeSrc = attrIdentifier->mIdentifier;
  7157. targetFunctionName = attrIdentifier->mIdentifier->ToString();
  7158. }
  7159. else
  7160. targetFunctionName = qualifiedName->mRight->ToString();
  7161. bool hadError = false;
  7162. thisValue = LookupIdentifier(qualifiedName->mLeft, true, &hadError);
  7163. if (!thisValue)
  7164. thisValue = GetResult();
  7165. if (hadError)
  7166. return;
  7167. if (!thisValue)
  7168. {
  7169. // Identifier not found. Static method? Just check speculatively don't throw error
  7170. DbgType* type;
  7171. {
  7172. SetAndRestoreValue<bool> prevIgnoreErrors(mIgnoreErrors, true);
  7173. type = ResolveTypeRef(qualifiedName->mLeft);
  7174. }
  7175. /*if (type->IsGenericParam())
  7176. {
  7177. auto genericParamInstance = mModule->GetGenericParamInstance((BfGenericParamType*)type);
  7178. type = genericParamInstance->mTypeConstraint;
  7179. }*/
  7180. if (type != NULL)
  7181. thisValue.mType = type;
  7182. else if (auto qualifiedLeft = BfNodeDynCast<BfQualifiedNameNode>(qualifiedName->mLeft))
  7183. {
  7184. LookupQualifiedStaticField(qualifiedLeft, true);
  7185. thisValue = mResult;
  7186. mResult = DbgTypedValue();
  7187. }
  7188. thisValue.mHasNoValue = true;
  7189. }
  7190. if (!thisValue.mType)
  7191. {
  7192. Fail("Identifier not found", qualifiedName->mLeft);
  7193. return;
  7194. }
  7195. mResult = DbgTypedValue();
  7196. }
  7197. else if (auto identiferExpr = BfNodeDynCast<BfIdentifierNode>(target))
  7198. {
  7199. allowImplicitThis = true;
  7200. targetFunctionName = target->ToString();
  7201. }
  7202. else if (auto invocationExpr = BfNodeDynCast<BfInvocationExpression>(target))
  7203. {
  7204. // It appears we're attempting to invoke a delegate returned from another method
  7205. Visit(invocationExpr);
  7206. auto innerInvocationResult = mResult;
  7207. mResult = DbgTypedValue();
  7208. if (!innerInvocationResult)
  7209. return;
  7210. /*if (innerInvocationResult.mType->IsTypeInstance())
  7211. {
  7212. auto invocationTypeInst = innerInvocationResult.mType->ToTypeInstance();
  7213. if (invocationTypeInst->mTypeDef->mIsDelegate)
  7214. {
  7215. thisValue = innerInvocationResult;
  7216. targetFunctionName = "Invoke";
  7217. }
  7218. }*/
  7219. if (!thisValue)
  7220. {
  7221. Fail(StrFormat("Cannot perform invocation on type '%s'", innerInvocationResult.mType->ToString().c_str()), invocationExpr->mTarget);
  7222. return;
  7223. }
  7224. }
  7225. else
  7226. {
  7227. Fail("Invalid invocation target", target);
  7228. return;
  7229. }
  7230. if (thisValue)
  7231. {
  7232. if (thisValue.mType->IsPointer())
  7233. {
  7234. //BF_ASSERT(thisValue.mIsAddr);
  7235. thisValue.mType = thisValue.mType->mTypeParam;
  7236. thisValue.mSrcAddress = thisValue.mPtr;
  7237. }
  7238. if (thisValue.mType->IsPrimitiveType())
  7239. {
  7240. //TODO:
  7241. /*auto primStructType = GetPrimitiveStructType(thisValue.mType);
  7242. //thisValue = mModule->Cast(target, thisValue, primStructType);
  7243. auto srcAlloca = mModule->GetHeadIRBuilder()->CreateAlloca(primStructType->mInstLLVMType, 0);
  7244. srcAlloca->setAlignment(primStructType->mAlign);
  7245. auto primPtr = mModule->mIRBuilder->CreateConstInBoundsGEP2_32(srcAlloca, 0, 0);
  7246. mModule->mIRBuilder->CreateStore(thisValue.mValue, primPtr);
  7247. thisValue = DbgTypedValue(srcAlloca, primStructType, true);*/
  7248. }
  7249. if (thisValue.mType->IsEnum())
  7250. {
  7251. //auto enumStructType = thisValue.mType->ToTypeInstance();
  7252. /*auto srcAlloca = mModule->GetHeadIRBuilder()->CreateAlloca(enumStructType->mInstLLVMType, 0);
  7253. srcAlloca->setAlignment(enumStructType->mAlign);
  7254. auto enumPtr = mModule->mIRBuilder->CreateConstInBoundsGEP2_32(srcAlloca, 0, 0);
  7255. mModule->mIRBuilder->CreateStore(thisValue.mValue, enumPtr);*/
  7256. //thisValue = DbgTypedValue(mModule->mIRBuilder->CreateBitCast(srcAlloca, enumStructType->mBaseType->mPtrLLVMType), enumStructType->mBaseType, true);
  7257. }
  7258. /*if (!thisValue.mType->IsTypeInstance())
  7259. {
  7260. Fail(StrFormat("Invalid target type: '%s'", mModule->TypeToString(thisValue.mType).c_str()), target);
  7261. return;
  7262. }*/
  7263. }
  7264. mResult = MatchMethod(methodNodeSrc, thisValue, allowImplicitThis, bypassVirtual, targetFunctionName, args, methodGenericArguments);
  7265. }
  7266. void DbgExprEvaluator::Visit(BfInvocationExpression* invocationExpr)
  7267. {
  7268. mIsComplexExpression = true;
  7269. auto wasCapturingMethodInfo = (mAutoComplete != NULL) && (mAutoComplete->mIsCapturingMethodMatchInfo);
  7270. /*if (mAutoComplete != NULL)
  7271. mAutoComplete->CheckInvocation(invocationExpr, invocationExpr->mOpenParen, invocationExpr->mCloseParen, invocationExpr->mCommas);*/
  7272. BfSizedArray<ASTREF(BfAstNode*)>* methodGenericArguments = NULL;
  7273. if (invocationExpr->mGenericArgs != NULL)
  7274. methodGenericArguments = &invocationExpr->mGenericArgs->mGenericArgs;
  7275. DoInvocation(invocationExpr->mTarget, invocationExpr->mArguments, methodGenericArguments);
  7276. if ((wasCapturingMethodInfo) && (!mAutoComplete->mIsCapturingMethodMatchInfo))
  7277. {
  7278. mAutoComplete->mIsCapturingMethodMatchInfo = true;
  7279. BF_ASSERT(mAutoComplete->mMethodMatchInfo != NULL);
  7280. }
  7281. else if (mAutoComplete != NULL)
  7282. mAutoComplete->mIsCapturingMethodMatchInfo = false;
  7283. }
  7284. void DbgExprEvaluator::Visit(BfConditionalExpression* condExpr)
  7285. {
  7286. VisitChild(condExpr->mConditionExpression);
  7287. GetResult();
  7288. if (!mResult)
  7289. return;
  7290. auto boolResult = Cast(condExpr->mConditionExpression, mResult, mDbgModule->GetPrimitiveType(DbgType_Bool, GetLanguage()));
  7291. if (!boolResult)
  7292. return;
  7293. if (boolResult.mBool)
  7294. {
  7295. if (condExpr->mTrueExpression != NULL)
  7296. VisitChild(condExpr->mTrueExpression);
  7297. else
  7298. mResult = DbgTypedValue();
  7299. }
  7300. else
  7301. {
  7302. if (condExpr->mFalseExpression != NULL)
  7303. VisitChild(condExpr->mFalseExpression);
  7304. else
  7305. mResult = DbgTypedValue();
  7306. }
  7307. }
  7308. void DbgExprEvaluator::Visit(BfTypeAttrExpression* typeAttrExpr)
  7309. {
  7310. if (typeAttrExpr->mTypeRef == NULL)
  7311. return;
  7312. AutocompleteCheckType(typeAttrExpr->mTypeRef);
  7313. auto dbgType = ResolveTypeRef(typeAttrExpr->mTypeRef);
  7314. if (dbgType == NULL)
  7315. return;
  7316. mResult.mType = mDbgModule->GetPrimitiveType(DbgType_i32, GetLanguage());
  7317. switch (typeAttrExpr->mToken->GetToken())
  7318. {
  7319. case BfToken_SizeOf:
  7320. mResult.mInt64 = dbgType->GetByteCount();
  7321. break;
  7322. case BfToken_AlignOf:
  7323. mResult.mInt64 = dbgType->GetAlign();
  7324. break;
  7325. case BfToken_StrideOf:
  7326. mResult.mInt64 = dbgType->GetStride();
  7327. break;
  7328. default:
  7329. Fail("Invalid attribute expression", typeAttrExpr);
  7330. break;
  7331. }
  7332. }
  7333. void DbgExprEvaluator::Visit(BfTupleExpression* tupleExpr)
  7334. {
  7335. if (mReceivingValue == NULL)
  7336. {
  7337. Fail("Tuple expressions can only be used when the receiving address can be inferred", tupleExpr);
  7338. return;
  7339. }
  7340. if (mReceivingValue->mIsReadOnly)
  7341. {
  7342. Fail("Cannot write to read-only value", tupleExpr);
  7343. return;
  7344. }
  7345. auto type = mReceivingValue->mType->RemoveModifiers();
  7346. if (!type->IsBfTuple())
  7347. {
  7348. Fail(StrFormat("Tuple expressions cannot be used for type '%s'", mReceivingValue->mType->ToString().c_str()), tupleExpr);
  7349. return;
  7350. }
  7351. CheckTupleCreation(mReceivingValue->mSrcAddress, tupleExpr, mReceivingValue->mType, tupleExpr->mValues, &tupleExpr->mNames);
  7352. mReceivingValue = NULL;
  7353. }
  7354. DbgTypedValue DbgExprEvaluator::Resolve(BfExpression* expr, DbgType* wantType)
  7355. {
  7356. //BfLogDbgExpr("Dbg Evaluate %s\n", expr->ToString().c_str());
  7357. BF_ASSERT(!HasPropResult());
  7358. mCallStackPreservePos = 0;
  7359. SetAndRestoreValue<DbgType*> prevType(mExpectingType, wantType);
  7360. SetAndRestoreValue<DbgTypedValue> prevResult(mResult, DbgTypedValue());
  7361. if ((mExpressionFlags & DwEvalExpressionFlag_AllowCalls) != 0)
  7362. {
  7363. BF_ASSERT(mCallResults != NULL);
  7364. }
  7365. if (mExplicitThis)
  7366. mExplicitThis = FixThis(mExplicitThis);
  7367. mExpectingType = wantType;
  7368. VisitChildNoRef(expr);
  7369. GetResult();
  7370. while (true)
  7371. {
  7372. if (!mResult)
  7373. break;
  7374. if (//(mResult.mType->mTypeCode == DbgType_Const) ||
  7375. (mResult.mType->mTypeCode == DbgType_Volatile))
  7376. mResult.mType = mResult.mType->mTypeParam;
  7377. else
  7378. break;
  7379. }
  7380. if ((mResult) && (wantType != NULL))
  7381. mResult = Cast(expr, mResult, wantType);
  7382. if ((mReferenceId != NULL) && (mIsComplexExpression))
  7383. mReferenceId->clear();
  7384. return mResult;
  7385. }
  7386. BfAstNode* DbgExprEvaluator::FinalizeExplicitThisReferences(BfAstNode* headNode)
  7387. {
  7388. //return headNode;
  7389. if (mExplicitThisExpr == NULL)
  7390. return headNode;
  7391. auto explicitThisExpr = mExplicitThisExpr;
  7392. mExplicitThisExpr = NULL;
  7393. BfReducer bfReducer;
  7394. BfPrinter bfPrinter(explicitThisExpr->GetSourceData()->mRootNode, NULL, NULL);
  7395. bfPrinter.mIgnoreTrivia = true;
  7396. bfPrinter.mReformatting = true;
  7397. bfPrinter.VisitChild(explicitThisExpr);
  7398. bool doWrap = false;
  7399. String thisExprStr = bfPrinter.mOutString;
  7400. if (auto unaryOpExpr = BfNodeDynCast<BfUnaryOperatorExpression>(explicitThisExpr))
  7401. {
  7402. if ((unaryOpExpr->mOp != BfUnaryOp_AddressOf) && (unaryOpExpr->mOp != BfUnaryOp_Dereference))
  7403. doWrap = true;
  7404. }
  7405. if ((explicitThisExpr->IsA<BfCastExpression>()) ||
  7406. (explicitThisExpr->IsA<BfBinaryOperatorExpression>()) ||
  7407. (explicitThisExpr->IsA<BfUnaryOperatorExpression>()))
  7408. doWrap = true;
  7409. if (doWrap)
  7410. {
  7411. thisExprStr = "(" + thisExprStr + ")";
  7412. }
  7413. auto bfParser = headNode->GetSourceData()->ToParser();
  7414. BF_ASSERT(bfParser != NULL);
  7415. auto source = headNode->GetSourceData();
  7416. for (auto& replaceNodeRecord : mDeferredInsertExplicitThisVector)
  7417. {
  7418. auto replaceNode = replaceNodeRecord.mNode;
  7419. DbgType* castType = NULL;
  7420. auto typeRef = BfNodeDynCast<BfTypeReference>(replaceNode);
  7421. if ((typeRef != NULL) || (replaceNodeRecord.mForceTypeRef))
  7422. {
  7423. castType = ResolveTypeRef(replaceNode);
  7424. if (castType == NULL)
  7425. continue;
  7426. }
  7427. // Use an identifier as a text placeholder for the whole 'this' expression
  7428. // We must do this because we can't insert the actual 'this' node into multiple parents
  7429. auto thisExprNode = source->mAlloc.Alloc<BfIdentifierNode>();
  7430. BfAstNode* newNode = NULL;
  7431. if (castType != NULL)
  7432. {
  7433. bfReducer.ReplaceNode(replaceNode, thisExprNode);
  7434. newNode = thisExprNode;
  7435. }
  7436. else if (auto thisNode = BfNodeDynCast<BfThisExpression>(replaceNode))
  7437. {
  7438. bfReducer.ReplaceNode(replaceNode, thisExprNode);
  7439. newNode = thisExprNode;
  7440. }
  7441. else if (auto identifierNode = BfNodeDynCast<BfIdentifierNode>(replaceNode))
  7442. {
  7443. auto memberRefNode = source->mAlloc.Alloc<BfMemberReferenceExpression>();
  7444. bfReducer.ReplaceNode(replaceNode, memberRefNode);
  7445. memberRefNode->mMemberName = identifierNode;
  7446. auto tokeNode = source->mAlloc.Alloc<BfTokenNode>();
  7447. tokeNode->SetToken(BfToken_Dot);
  7448. bfReducer.MoveNode(tokeNode, memberRefNode);
  7449. memberRefNode->mDotToken = tokeNode;
  7450. bfReducer.MoveNode(thisExprNode, memberRefNode);
  7451. memberRefNode->mTarget = thisExprNode;
  7452. newNode = memberRefNode;
  7453. }
  7454. if (newNode != NULL)
  7455. {
  7456. if (replaceNodeRecord.mNodeRef != NULL)
  7457. *replaceNodeRecord.mNodeRef = newNode;
  7458. if (replaceNode == headNode)
  7459. headNode = newNode;
  7460. }
  7461. String replaceString;
  7462. if (castType != NULL)
  7463. {
  7464. replaceString = castType->ToString();
  7465. }
  7466. else
  7467. replaceString = thisExprStr;
  7468. int thisLen = (int)replaceString.length();
  7469. int srcStart = bfParser->AllocChars(thisLen);
  7470. memcpy((char*)source->mSrc + srcStart, replaceString.c_str(), thisLen);
  7471. thisExprNode->Init(srcStart, srcStart, srcStart + thisLen);
  7472. }
  7473. return headNode;
  7474. }