jshint.js 234 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517251825192520252125222523252425252526252725282529253025312532253325342535253625372538253925402541254225432544254525462547254825492550255125522553255425552556255725582559256025612562256325642565256625672568256925702571257225732574257525762577257825792580258125822583258425852586258725882589259025912592259325942595259625972598259926002601260226032604260526062607260826092610261126122613261426152616261726182619262026212622262326242625262626272628262926302631263226332634263526362637263826392640264126422643264426452646264726482649265026512652265326542655265626572658265926602661266226632664266526662667266826692670267126722673267426752676267726782679268026812682268326842685268626872688268926902691269226932694269526962697269826992700270127022703270427052706270727082709271027112712271327142715271627172718271927202721272227232724272527262727272827292730273127322733273427352736273727382739274027412742274327442745274627472748274927502751275227532754275527562757275827592760276127622763276427652766276727682769277027712772277327742775277627772778277927802781278227832784278527862787278827892790279127922793279427952796279727982799280028012802280328042805280628072808280928102811281228132814281528162817281828192820282128222823282428252826282728282829283028312832283328342835283628372838283928402841284228432844284528462847284828492850285128522853285428552856285728582859286028612862286328642865286628672868286928702871287228732874287528762877287828792880288128822883288428852886288728882889289028912892289328942895289628972898289929002901290229032904290529062907290829092910291129122913291429152916291729182919292029212922292329242925292629272928292929302931293229332934293529362937293829392940294129422943294429452946294729482949295029512952295329542955295629572958295929602961296229632964296529662967296829692970297129722973297429752976297729782979298029812982298329842985298629872988298929902991299229932994299529962997299829993000300130023003300430053006300730083009301030113012301330143015301630173018301930203021302230233024302530263027302830293030303130323033303430353036303730383039304030413042304330443045304630473048304930503051305230533054305530563057305830593060306130623063306430653066306730683069307030713072307330743075307630773078307930803081308230833084308530863087308830893090309130923093309430953096309730983099310031013102310331043105310631073108310931103111311231133114311531163117311831193120312131223123312431253126312731283129313031313132313331343135313631373138313931403141314231433144314531463147314831493150315131523153315431553156315731583159316031613162316331643165316631673168316931703171317231733174317531763177317831793180318131823183318431853186318731883189319031913192319331943195319631973198319932003201320232033204320532063207320832093210321132123213321432153216321732183219322032213222322332243225322632273228322932303231323232333234323532363237323832393240324132423243324432453246324732483249325032513252325332543255325632573258325932603261326232633264326532663267326832693270327132723273327432753276327732783279328032813282328332843285328632873288328932903291329232933294329532963297329832993300330133023303330433053306330733083309331033113312331333143315331633173318331933203321332233233324332533263327332833293330333133323333333433353336333733383339334033413342334333443345334633473348334933503351335233533354335533563357335833593360336133623363336433653366336733683369337033713372337333743375337633773378337933803381338233833384338533863387338833893390339133923393339433953396339733983399340034013402340334043405340634073408340934103411341234133414341534163417341834193420342134223423342434253426342734283429343034313432343334343435343634373438343934403441344234433444344534463447344834493450345134523453345434553456345734583459346034613462346334643465346634673468346934703471347234733474347534763477347834793480348134823483348434853486348734883489349034913492349334943495349634973498349935003501350235033504350535063507350835093510351135123513351435153516351735183519352035213522352335243525352635273528352935303531353235333534353535363537353835393540354135423543354435453546354735483549355035513552355335543555355635573558355935603561356235633564356535663567356835693570357135723573357435753576357735783579358035813582358335843585358635873588358935903591359235933594359535963597359835993600360136023603360436053606360736083609361036113612361336143615361636173618361936203621362236233624362536263627362836293630363136323633363436353636363736383639364036413642364336443645364636473648364936503651365236533654365536563657365836593660366136623663366436653666366736683669367036713672367336743675367636773678367936803681368236833684368536863687368836893690369136923693369436953696369736983699370037013702370337043705370637073708370937103711371237133714371537163717371837193720372137223723372437253726372737283729373037313732373337343735373637373738373937403741374237433744374537463747374837493750375137523753375437553756375737583759376037613762376337643765376637673768376937703771377237733774377537763777377837793780378137823783378437853786378737883789379037913792379337943795379637973798379938003801380238033804380538063807380838093810381138123813381438153816381738183819382038213822382338243825382638273828382938303831383238333834383538363837383838393840384138423843384438453846384738483849385038513852385338543855385638573858385938603861386238633864386538663867386838693870387138723873387438753876387738783879388038813882388338843885388638873888388938903891389238933894389538963897389838993900390139023903390439053906390739083909391039113912391339143915391639173918391939203921392239233924392539263927392839293930393139323933393439353936393739383939394039413942394339443945394639473948394939503951395239533954395539563957395839593960396139623963396439653966396739683969397039713972397339743975397639773978397939803981398239833984398539863987398839893990399139923993399439953996399739983999400040014002400340044005400640074008400940104011401240134014401540164017401840194020402140224023402440254026402740284029403040314032403340344035403640374038403940404041404240434044404540464047404840494050405140524053405440554056405740584059406040614062406340644065406640674068406940704071407240734074407540764077407840794080408140824083408440854086408740884089409040914092409340944095409640974098409941004101410241034104410541064107410841094110411141124113411441154116411741184119412041214122412341244125412641274128412941304131413241334134413541364137413841394140414141424143414441454146414741484149415041514152415341544155415641574158415941604161416241634164416541664167416841694170417141724173417441754176417741784179418041814182418341844185418641874188418941904191419241934194419541964197419841994200420142024203420442054206420742084209421042114212421342144215421642174218421942204221422242234224422542264227422842294230423142324233423442354236423742384239424042414242424342444245424642474248424942504251425242534254425542564257425842594260426142624263426442654266426742684269427042714272427342744275427642774278427942804281428242834284428542864287428842894290429142924293429442954296429742984299430043014302430343044305430643074308430943104311431243134314431543164317431843194320432143224323432443254326432743284329433043314332433343344335433643374338433943404341434243434344434543464347434843494350435143524353435443554356435743584359436043614362436343644365436643674368436943704371437243734374437543764377437843794380438143824383438443854386438743884389439043914392439343944395439643974398439944004401440244034404440544064407440844094410441144124413441444154416441744184419442044214422442344244425442644274428442944304431443244334434443544364437443844394440444144424443444444454446444744484449445044514452445344544455445644574458445944604461446244634464446544664467446844694470447144724473447444754476447744784479448044814482448344844485448644874488448944904491449244934494449544964497449844994500450145024503450445054506450745084509451045114512451345144515451645174518451945204521452245234524452545264527452845294530453145324533453445354536453745384539454045414542454345444545454645474548454945504551455245534554455545564557455845594560456145624563456445654566456745684569457045714572457345744575457645774578457945804581458245834584458545864587458845894590459145924593459445954596459745984599460046014602460346044605460646074608460946104611461246134614461546164617461846194620462146224623462446254626462746284629463046314632463346344635463646374638463946404641464246434644464546464647464846494650465146524653465446554656465746584659466046614662466346644665466646674668466946704671467246734674467546764677467846794680468146824683468446854686468746884689469046914692469346944695469646974698469947004701470247034704470547064707470847094710471147124713471447154716471747184719472047214722472347244725472647274728472947304731473247334734473547364737473847394740474147424743474447454746474747484749475047514752475347544755475647574758475947604761476247634764476547664767476847694770477147724773477447754776477747784779478047814782478347844785478647874788478947904791479247934794479547964797479847994800480148024803480448054806480748084809481048114812481348144815481648174818481948204821482248234824482548264827482848294830483148324833483448354836483748384839484048414842484348444845484648474848484948504851485248534854485548564857485848594860486148624863486448654866486748684869487048714872487348744875487648774878487948804881488248834884488548864887488848894890489148924893489448954896489748984899490049014902490349044905490649074908490949104911491249134914491549164917491849194920492149224923492449254926492749284929493049314932493349344935493649374938493949404941494249434944494549464947494849494950495149524953495449554956495749584959496049614962496349644965496649674968496949704971497249734974497549764977497849794980498149824983498449854986498749884989499049914992499349944995499649974998499950005001500250035004500550065007500850095010501150125013501450155016501750185019502050215022502350245025502650275028502950305031503250335034503550365037503850395040504150425043504450455046504750485049505050515052505350545055505650575058505950605061506250635064506550665067506850695070507150725073507450755076507750785079508050815082508350845085508650875088508950905091509250935094509550965097509850995100510151025103510451055106510751085109511051115112511351145115511651175118511951205121512251235124512551265127512851295130513151325133513451355136513751385139514051415142514351445145514651475148514951505151515251535154515551565157515851595160516151625163516451655166516751685169517051715172517351745175517651775178517951805181518251835184518551865187518851895190519151925193519451955196519751985199520052015202520352045205520652075208520952105211521252135214521552165217521852195220522152225223522452255226522752285229523052315232523352345235523652375238523952405241524252435244524552465247524852495250525152525253525452555256525752585259526052615262526352645265526652675268526952705271527252735274527552765277527852795280528152825283528452855286528752885289529052915292529352945295529652975298529953005301530253035304530553065307530853095310531153125313531453155316531753185319532053215322532353245325532653275328532953305331533253335334533553365337533853395340534153425343534453455346534753485349535053515352535353545355535653575358535953605361536253635364536553665367536853695370537153725373537453755376537753785379538053815382538353845385538653875388538953905391539253935394539553965397539853995400540154025403540454055406540754085409541054115412541354145415541654175418541954205421542254235424542554265427542854295430543154325433543454355436543754385439544054415442544354445445544654475448544954505451545254535454545554565457545854595460546154625463546454655466546754685469547054715472547354745475547654775478547954805481548254835484548554865487548854895490549154925493549454955496549754985499550055015502550355045505550655075508550955105511551255135514551555165517551855195520552155225523552455255526552755285529553055315532553355345535553655375538553955405541554255435544554555465547554855495550555155525553555455555556555755585559556055615562556355645565556655675568556955705571557255735574557555765577557855795580558155825583558455855586558755885589559055915592559355945595559655975598559956005601560256035604560556065607560856095610561156125613561456155616561756185619562056215622562356245625562656275628562956305631563256335634563556365637563856395640564156425643564456455646564756485649565056515652565356545655565656575658565956605661566256635664566556665667566856695670567156725673567456755676567756785679568056815682568356845685568656875688568956905691569256935694569556965697569856995700570157025703570457055706570757085709571057115712571357145715571657175718571957205721572257235724572557265727572857295730573157325733573457355736573757385739574057415742574357445745574657475748574957505751575257535754575557565757575857595760576157625763576457655766576757685769577057715772577357745775577657775778577957805781578257835784578557865787578857895790579157925793579457955796579757985799580058015802580358045805580658075808580958105811581258135814581558165817581858195820582158225823582458255826582758285829583058315832583358345835583658375838583958405841584258435844584558465847584858495850585158525853585458555856585758585859586058615862586358645865586658675868586958705871587258735874587558765877587858795880588158825883588458855886588758885889589058915892589358945895589658975898589959005901590259035904590559065907590859095910591159125913591459155916591759185919592059215922592359245925592659275928592959305931593259335934593559365937593859395940594159425943594459455946594759485949595059515952595359545955595659575958595959605961596259635964596559665967596859695970597159725973597459755976597759785979598059815982598359845985598659875988598959905991599259935994599559965997599859996000600160026003600460056006600760086009601060116012601360146015601660176018601960206021602260236024602560266027602860296030603160326033603460356036603760386039604060416042604360446045604660476048604960506051605260536054605560566057605860596060606160626063606460656066606760686069607060716072607360746075607660776078607960806081608260836084608560866087608860896090609160926093609460956096609760986099610061016102610361046105610661076108610961106111611261136114611561166117611861196120612161226123612461256126612761286129613061316132613361346135613661376138613961406141614261436144614561466147614861496150615161526153615461556156615761586159616061616162616361646165616661676168616961706171617261736174617561766177617861796180618161826183618461856186618761886189619061916192619361946195619661976198619962006201620262036204620562066207620862096210621162126213621462156216621762186219622062216222622362246225622662276228622962306231623262336234623562366237623862396240624162426243624462456246624762486249625062516252625362546255625662576258625962606261626262636264626562666267626862696270627162726273627462756276627762786279628062816282628362846285628662876288628962906291629262936294629562966297629862996300630163026303630463056306630763086309631063116312631363146315631663176318631963206321632263236324632563266327632863296330633163326333633463356336633763386339634063416342634363446345634663476348634963506351635263536354635563566357635863596360636163626363636463656366636763686369637063716372637363746375637663776378637963806381638263836384638563866387638863896390639163926393639463956396639763986399640064016402640364046405640664076408640964106411641264136414641564166417641864196420642164226423642464256426642764286429643064316432643364346435643664376438643964406441644264436444644564466447644864496450645164526453645464556456645764586459646064616462646364646465646664676468646964706471647264736474647564766477647864796480648164826483648464856486648764886489649064916492649364946495649664976498649965006501650265036504650565066507650865096510651165126513651465156516651765186519652065216522652365246525652665276528652965306531653265336534653565366537653865396540654165426543654465456546654765486549655065516552655365546555655665576558655965606561656265636564656565666567656865696570657165726573657465756576657765786579658065816582658365846585658665876588658965906591659265936594659565966597659865996600660166026603660466056606660766086609661066116612661366146615661666176618661966206621662266236624662566266627662866296630663166326633663466356636663766386639664066416642664366446645664666476648664966506651665266536654665566566657665866596660666166626663666466656666666766686669667066716672667366746675667666776678667966806681668266836684668566866687668866896690669166926693669466956696669766986699670067016702670367046705670667076708670967106711671267136714671567166717671867196720672167226723672467256726672767286729673067316732673367346735673667376738673967406741674267436744674567466747674867496750675167526753675467556756675767586759676067616762676367646765676667676768676967706771677267736774677567766777677867796780678167826783678467856786678767886789679067916792679367946795679667976798679968006801680268036804680568066807680868096810681168126813681468156816681768186819682068216822682368246825682668276828682968306831683268336834683568366837683868396840684168426843684468456846684768486849685068516852685368546855685668576858685968606861686268636864686568666867686868696870687168726873687468756876687768786879688068816882688368846885688668876888688968906891689268936894689568966897689868996900690169026903690469056906690769086909691069116912691369146915691669176918691969206921692269236924692569266927692869296930693169326933693469356936693769386939694069416942694369446945694669476948694969506951695269536954695569566957695869596960696169626963696469656966696769686969697069716972697369746975697669776978697969806981698269836984698569866987698869896990699169926993699469956996699769986999700070017002700370047005700670077008700970107011701270137014701570167017701870197020702170227023702470257026702770287029703070317032703370347035703670377038703970407041704270437044704570467047704870497050705170527053705470557056705770587059706070617062706370647065706670677068706970707071707270737074707570767077707870797080708170827083708470857086708770887089709070917092709370947095709670977098709971007101710271037104710571067107710871097110711171127113711471157116711771187119712071217122712371247125712671277128712971307131713271337134713571367137713871397140714171427143714471457146714771487149715071517152715371547155715671577158715971607161716271637164716571667167716871697170717171727173717471757176717771787179718071817182718371847185718671877188718971907191719271937194719571967197719871997200720172027203720472057206720772087209721072117212721372147215721672177218721972207221722272237224722572267227722872297230723172327233723472357236723772387239724072417242724372447245724672477248724972507251725272537254725572567257725872597260726172627263726472657266726772687269727072717272727372747275727672777278727972807281728272837284728572867287728872897290729172927293729472957296729772987299730073017302730373047305730673077308730973107311731273137314731573167317731873197320732173227323732473257326732773287329733073317332733373347335733673377338733973407341734273437344734573467347734873497350735173527353735473557356735773587359736073617362736373647365736673677368736973707371737273737374737573767377737873797380738173827383738473857386738773887389739073917392739373947395739673977398739974007401740274037404740574067407740874097410741174127413741474157416741774187419742074217422742374247425742674277428742974307431743274337434743574367437743874397440744174427443744474457446744774487449745074517452745374547455745674577458745974607461746274637464746574667467746874697470747174727473747474757476747774787479748074817482748374847485748674877488748974907491749274937494749574967497749874997500750175027503750475057506750775087509751075117512751375147515751675177518751975207521752275237524752575267527752875297530753175327533753475357536753775387539754075417542754375447545754675477548754975507551755275537554755575567557755875597560756175627563756475657566756775687569757075717572757375747575757675777578757975807581758275837584758575867587758875897590759175927593759475957596759775987599760076017602760376047605760676077608760976107611761276137614761576167617761876197620762176227623762476257626762776287629763076317632763376347635763676377638763976407641764276437644764576467647764876497650765176527653765476557656765776587659766076617662766376647665766676677668766976707671767276737674767576767677767876797680768176827683768476857686768776887689769076917692769376947695769676977698769977007701770277037704770577067707770877097710771177127713771477157716771777187719772077217722772377247725772677277728772977307731773277337734773577367737773877397740774177427743774477457746774777487749775077517752775377547755775677577758775977607761776277637764776577667767776877697770777177727773777477757776777777787779778077817782778377847785778677877788778977907791779277937794779577967797779877997800780178027803780478057806780778087809781078117812781378147815781678177818781978207821782278237824782578267827782878297830783178327833783478357836783778387839784078417842784378447845784678477848784978507851785278537854785578567857785878597860786178627863786478657866786778687869787078717872787378747875787678777878787978807881788278837884788578867887788878897890789178927893789478957896789778987899790079017902790379047905790679077908790979107911791279137914791579167917791879197920792179227923792479257926792779287929793079317932793379347935793679377938793979407941794279437944794579467947794879497950795179527953795479557956795779587959796079617962796379647965796679677968796979707971797279737974797579767977797879797980798179827983798479857986798779887989799079917992799379947995799679977998799980008001800280038004800580068007800880098010801180128013801480158016801780188019802080218022802380248025802680278028802980308031803280338034803580368037803880398040804180428043804480458046804780488049805080518052805380548055805680578058805980608061806280638064806580668067806880698070807180728073807480758076807780788079808080818082808380848085808680878088808980908091809280938094809580968097809880998100810181028103810481058106810781088109811081118112811381148115811681178118811981208121812281238124812581268127812881298130813181328133813481358136813781388139814081418142814381448145814681478148814981508151815281538154815581568157815881598160816181628163816481658166816781688169817081718172817381748175817681778178817981808181818281838184818581868187818881898190819181928193819481958196819781988199820082018202820382048205820682078208820982108211821282138214821582168217821882198220822182228223822482258226822782288229823082318232823382348235823682378238823982408241824282438244824582468247824882498250825182528253825482558256825782588259826082618262826382648265826682678268826982708271827282738274827582768277827882798280828182828283828482858286828782888289829082918292829382948295829682978298829983008301830283038304830583068307830883098310831183128313831483158316831783188319832083218322832383248325832683278328832983308331833283338334833583368337833883398340834183428343834483458346834783488349835083518352835383548355835683578358835983608361836283638364836583668367836883698370837183728373837483758376837783788379838083818382838383848385838683878388838983908391839283938394839583968397839883998400840184028403840484058406840784088409841084118412841384148415841684178418841984208421842284238424842584268427842884298430843184328433843484358436843784388439844084418442844384448445844684478448844984508451845284538454845584568457845884598460846184628463846484658466846784688469847084718472847384748475847684778478847984808481848284838484848584868487848884898490849184928493849484958496849784988499850085018502850385048505850685078508850985108511851285138514851585168517851885198520852185228523852485258526852785288529853085318532853385348535853685378538853985408541854285438544854585468547854885498550855185528553855485558556855785588559856085618562856385648565856685678568856985708571857285738574857585768577857885798580858185828583858485858586858785888589859085918592859385948595859685978598859986008601860286038604860586068607860886098610861186128613861486158616861786188619862086218622862386248625862686278628862986308631863286338634863586368637863886398640864186428643864486458646864786488649865086518652865386548655865686578658865986608661866286638664866586668667866886698670867186728673867486758676867786788679868086818682868386848685868686878688868986908691869286938694869586968697869886998700870187028703870487058706870787088709871087118712871387148715871687178718871987208721872287238724872587268727872887298730873187328733873487358736873787388739874087418742874387448745874687478748874987508751875287538754875587568757875887598760876187628763876487658766876787688769877087718772877387748775877687778778877987808781878287838784878587868787878887898790879187928793879487958796879787988799880088018802880388048805880688078808880988108811881288138814881588168817881888198820882188228823882488258826882788288829883088318832883388348835883688378838883988408841884288438844884588468847884888498850885188528853885488558856885788588859886088618862886388648865886688678868886988708871887288738874887588768877887888798880888188828883888488858886888788888889889088918892889388948895889688978898889989008901890289038904890589068907890889098910891189128913891489158916891789188919892089218922892389248925892689278928892989308931893289338934893589368937893889398940894189428943894489458946894789488949895089518952895389548955895689578958895989608961896289638964896589668967896889698970897189728973897489758976897789788979898089818982898389848985898689878988898989908991899289938994899589968997899889999000900190029003900490059006900790089009901090119012901390149015901690179018901990209021902290239024902590269027902890299030903190329033903490359036903790389039904090419042904390449045904690479048904990509051905290539054905590569057905890599060906190629063906490659066906790689069907090719072907390749075
  1. define(function(require, exports, module) {
  2. // 2.1.9
  3. require = null;
  4. require=(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);throw new Error("Cannot find module '"+o+"'")}var f=n[o]={exports:{}};t[o][0].call(f.exports,function(e){var n=t[o][1][e];return s(n?n:e)},f,f.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o<r.length;o++)s(r[o]);return s})({
  5. 9:[function (req,module,exports){
  6. ["log", "info", "warn", "error",
  7. "time","timeEnd", "trace", "dir", "assert"
  8. ].forEach(function(x) {exports[x] = nop;});
  9. function nop() {}
  10. },{}],
  11. 1:[function(req,module,exports){
  12. // Underscore.js 1.4.4
  13. // http://underscorejs.org
  14. // (c) 2009-2013 Jeremy Ashkenas, DocumentCloud Inc.
  15. // Underscore may be freely distributed under the MIT license.
  16. (function() {
  17. // Baseline setup
  18. // --------------
  19. // Establish the root object, `window` in the browser, or `global` on the server.
  20. var root = this;
  21. // Save the previous value of the `_` variable.
  22. var previousUnderscore = root._;
  23. // Establish the object that gets returned to break out of a loop iteration.
  24. var breaker = {};
  25. // Save bytes in the minified (but not gzipped) version:
  26. var ArrayProto = Array.prototype, ObjProto = Object.prototype, FuncProto = Function.prototype;
  27. // Create quick reference variables for speed access to core prototypes.
  28. var push = ArrayProto.push,
  29. slice = ArrayProto.slice,
  30. concat = ArrayProto.concat,
  31. toString = ObjProto.toString,
  32. hasOwnProperty = ObjProto.hasOwnProperty;
  33. // All **ECMAScript 5** native function implementations that we hope to use
  34. // are declared here.
  35. var
  36. nativeForEach = ArrayProto.forEach,
  37. nativeMap = ArrayProto.map,
  38. nativeReduce = ArrayProto.reduce,
  39. nativeReduceRight = ArrayProto.reduceRight,
  40. nativeFilter = ArrayProto.filter,
  41. nativeEvery = ArrayProto.every,
  42. nativeSome = ArrayProto.some,
  43. nativeIndexOf = ArrayProto.indexOf,
  44. nativeLastIndexOf = ArrayProto.lastIndexOf,
  45. nativeIsArray = Array.isArray,
  46. nativeKeys = Object.keys,
  47. nativeBind = FuncProto.bind;
  48. // Create a safe reference to the Underscore object for use below.
  49. var _ = function(obj) {
  50. if (obj instanceof _) return obj;
  51. if (!(this instanceof _)) return new _(obj);
  52. this._wrapped = obj;
  53. };
  54. // Export the Underscore object for **Node.js**, with
  55. // backwards-compatibility for the old `require()` API. If we're in
  56. // the browser, add `_` as a global object via a string identifier,
  57. // for Closure Compiler "advanced" mode.
  58. if (typeof exports !== 'undefined') {
  59. if (typeof module !== 'undefined' && module.exports) {
  60. exports = module.exports = _;
  61. }
  62. exports._ = _;
  63. } else {
  64. root._ = _;
  65. }
  66. // Current version.
  67. _.VERSION = '1.4.4';
  68. // Collection Functions
  69. // --------------------
  70. // The cornerstone, an `each` implementation, aka `forEach`.
  71. // Handles objects with the built-in `forEach`, arrays, and raw objects.
  72. // Delegates to **ECMAScript 5**'s native `forEach` if available.
  73. var each = _.each = _.forEach = function(obj, iterator, context) {
  74. if (obj == null) return;
  75. if (nativeForEach && obj.forEach === nativeForEach) {
  76. obj.forEach(iterator, context);
  77. } else if (obj.length === +obj.length) {
  78. for (var i = 0, l = obj.length; i < l; i++) {
  79. if (iterator.call(context, obj[i], i, obj) === breaker) return;
  80. }
  81. } else {
  82. for (var key in obj) {
  83. if (_.has(obj, key)) {
  84. if (iterator.call(context, obj[key], key, obj) === breaker) return;
  85. }
  86. }
  87. }
  88. };
  89. // Return the results of applying the iterator to each element.
  90. // Delegates to **ECMAScript 5**'s native `map` if available.
  91. _.map = _.collect = function(obj, iterator, context) {
  92. var results = [];
  93. if (obj == null) return results;
  94. if (nativeMap && obj.map === nativeMap) return obj.map(iterator, context);
  95. each(obj, function(value, index, list) {
  96. results[results.length] = iterator.call(context, value, index, list);
  97. });
  98. return results;
  99. };
  100. var reduceError = 'Reduce of empty array with no initial value';
  101. // **Reduce** builds up a single result from a list of values, aka `inject`,
  102. // or `foldl`. Delegates to **ECMAScript 5**'s native `reduce` if available.
  103. _.reduce = _.foldl = _.inject = function(obj, iterator, memo, context) {
  104. var initial = arguments.length > 2;
  105. if (obj == null) obj = [];
  106. if (nativeReduce && obj.reduce === nativeReduce) {
  107. if (context) iterator = _.bind(iterator, context);
  108. return initial ? obj.reduce(iterator, memo) : obj.reduce(iterator);
  109. }
  110. each(obj, function(value, index, list) {
  111. if (!initial) {
  112. memo = value;
  113. initial = true;
  114. } else {
  115. memo = iterator.call(context, memo, value, index, list);
  116. }
  117. });
  118. if (!initial) throw new TypeError(reduceError);
  119. return memo;
  120. };
  121. // The right-associative version of reduce, also known as `foldr`.
  122. // Delegates to **ECMAScript 5**'s native `reduceRight` if available.
  123. _.reduceRight = _.foldr = function(obj, iterator, memo, context) {
  124. var initial = arguments.length > 2;
  125. if (obj == null) obj = [];
  126. if (nativeReduceRight && obj.reduceRight === nativeReduceRight) {
  127. if (context) iterator = _.bind(iterator, context);
  128. return initial ? obj.reduceRight(iterator, memo) : obj.reduceRight(iterator);
  129. }
  130. var length = obj.length;
  131. if (length !== +length) {
  132. var keys = _.keys(obj);
  133. length = keys.length;
  134. }
  135. each(obj, function(value, index, list) {
  136. index = keys ? keys[--length] : --length;
  137. if (!initial) {
  138. memo = obj[index];
  139. initial = true;
  140. } else {
  141. memo = iterator.call(context, memo, obj[index], index, list);
  142. }
  143. });
  144. if (!initial) throw new TypeError(reduceError);
  145. return memo;
  146. };
  147. // Return the first value which passes a truth test. Aliased as `detect`.
  148. _.find = _.detect = function(obj, iterator, context) {
  149. var result;
  150. any(obj, function(value, index, list) {
  151. if (iterator.call(context, value, index, list)) {
  152. result = value;
  153. return true;
  154. }
  155. });
  156. return result;
  157. };
  158. // Return all the elements that pass a truth test.
  159. // Delegates to **ECMAScript 5**'s native `filter` if available.
  160. // Aliased as `select`.
  161. _.filter = _.select = function(obj, iterator, context) {
  162. var results = [];
  163. if (obj == null) return results;
  164. if (nativeFilter && obj.filter === nativeFilter) return obj.filter(iterator, context);
  165. each(obj, function(value, index, list) {
  166. if (iterator.call(context, value, index, list)) results[results.length] = value;
  167. });
  168. return results;
  169. };
  170. // Return all the elements for which a truth test fails.
  171. _.reject = function(obj, iterator, context) {
  172. return _.filter(obj, function(value, index, list) {
  173. return !iterator.call(context, value, index, list);
  174. }, context);
  175. };
  176. // Determine whether all of the elements match a truth test.
  177. // Delegates to **ECMAScript 5**'s native `every` if available.
  178. // Aliased as `all`.
  179. _.every = _.all = function(obj, iterator, context) {
  180. iterator || (iterator = _.identity);
  181. var result = true;
  182. if (obj == null) return result;
  183. if (nativeEvery && obj.every === nativeEvery) return obj.every(iterator, context);
  184. each(obj, function(value, index, list) {
  185. if (!(result = result && iterator.call(context, value, index, list))) return breaker;
  186. });
  187. return !!result;
  188. };
  189. // Determine if at least one element in the object matches a truth test.
  190. // Delegates to **ECMAScript 5**'s native `some` if available.
  191. // Aliased as `any`.
  192. var any = _.some = _.any = function(obj, iterator, context) {
  193. iterator || (iterator = _.identity);
  194. var result = false;
  195. if (obj == null) return result;
  196. if (nativeSome && obj.some === nativeSome) return obj.some(iterator, context);
  197. each(obj, function(value, index, list) {
  198. if (result || (result = iterator.call(context, value, index, list))) return breaker;
  199. });
  200. return !!result;
  201. };
  202. // Determine if the array or object contains a given value (using `===`).
  203. // Aliased as `include`.
  204. _.contains = _.include = function(obj, target) {
  205. if (obj == null) return false;
  206. if (nativeIndexOf && obj.indexOf === nativeIndexOf) return obj.indexOf(target) != -1;
  207. return any(obj, function(value) {
  208. return value === target;
  209. });
  210. };
  211. // Invoke a method (with arguments) on every item in a collection.
  212. _.invoke = function(obj, method) {
  213. var args = slice.call(arguments, 2);
  214. var isFunc = _.isFunction(method);
  215. return _.map(obj, function(value) {
  216. return (isFunc ? method : value[method]).apply(value, args);
  217. });
  218. };
  219. // Convenience version of a common use case of `map`: fetching a property.
  220. _.pluck = function(obj, key) {
  221. return _.map(obj, function(value){ return value[key]; });
  222. };
  223. // Convenience version of a common use case of `filter`: selecting only objects
  224. // containing specific `key:value` pairs.
  225. _.where = function(obj, attrs, first) {
  226. if (_.isEmpty(attrs)) return first ? null : [];
  227. return _[first ? 'find' : 'filter'](obj, function(value) {
  228. for (var key in attrs) {
  229. if (attrs[key] !== value[key]) return false;
  230. }
  231. return true;
  232. });
  233. };
  234. // Convenience version of a common use case of `find`: getting the first object
  235. // containing specific `key:value` pairs.
  236. _.findWhere = function(obj, attrs) {
  237. return _.where(obj, attrs, true);
  238. };
  239. // Return the maximum element or (element-based computation).
  240. // Can't optimize arrays of integers longer than 65,535 elements.
  241. // See: https://bugs.webkit.org/show_bug.cgi?id=80797
  242. _.max = function(obj, iterator, context) {
  243. if (!iterator && _.isArray(obj) && obj[0] === +obj[0] && obj.length < 65535) {
  244. return Math.max.apply(Math, obj);
  245. }
  246. if (!iterator && _.isEmpty(obj)) return -Infinity;
  247. var result = {computed : -Infinity, value: -Infinity};
  248. each(obj, function(value, index, list) {
  249. var computed = iterator ? iterator.call(context, value, index, list) : value;
  250. computed >= result.computed && (result = {value : value, computed : computed});
  251. });
  252. return result.value;
  253. };
  254. // Return the minimum element (or element-based computation).
  255. _.min = function(obj, iterator, context) {
  256. if (!iterator && _.isArray(obj) && obj[0] === +obj[0] && obj.length < 65535) {
  257. return Math.min.apply(Math, obj);
  258. }
  259. if (!iterator && _.isEmpty(obj)) return Infinity;
  260. var result = {computed : Infinity, value: Infinity};
  261. each(obj, function(value, index, list) {
  262. var computed = iterator ? iterator.call(context, value, index, list) : value;
  263. computed < result.computed && (result = {value : value, computed : computed});
  264. });
  265. return result.value;
  266. };
  267. // Shuffle an array.
  268. _.shuffle = function(obj) {
  269. var rand;
  270. var index = 0;
  271. var shuffled = [];
  272. each(obj, function(value) {
  273. rand = _.random(index++);
  274. shuffled[index - 1] = shuffled[rand];
  275. shuffled[rand] = value;
  276. });
  277. return shuffled;
  278. };
  279. // An internal function to generate lookup iterators.
  280. var lookupIterator = function(value) {
  281. return _.isFunction(value) ? value : function(obj){ return obj[value]; };
  282. };
  283. // Sort the object's values by a criterion produced by an iterator.
  284. _.sortBy = function(obj, value, context) {
  285. var iterator = lookupIterator(value);
  286. return _.pluck(_.map(obj, function(value, index, list) {
  287. return {
  288. value : value,
  289. index : index,
  290. criteria : iterator.call(context, value, index, list)
  291. };
  292. }).sort(function(left, right) {
  293. var a = left.criteria;
  294. var b = right.criteria;
  295. if (a !== b) {
  296. if (a > b || a === void 0) return 1;
  297. if (a < b || b === void 0) return -1;
  298. }
  299. return left.index < right.index ? -1 : 1;
  300. }), 'value');
  301. };
  302. // An internal function used for aggregate "group by" operations.
  303. var group = function(obj, value, context, behavior) {
  304. var result = {};
  305. var iterator = lookupIterator(value || _.identity);
  306. each(obj, function(value, index) {
  307. var key = iterator.call(context, value, index, obj);
  308. behavior(result, key, value);
  309. });
  310. return result;
  311. };
  312. // Groups the object's values by a criterion. Pass either a string attribute
  313. // to group by, or a function that returns the criterion.
  314. _.groupBy = function(obj, value, context) {
  315. return group(obj, value, context, function(result, key, value) {
  316. (_.has(result, key) ? result[key] : (result[key] = [])).push(value);
  317. });
  318. };
  319. // Counts instances of an object that group by a certain criterion. Pass
  320. // either a string attribute to count by, or a function that returns the
  321. // criterion.
  322. _.countBy = function(obj, value, context) {
  323. return group(obj, value, context, function(result, key) {
  324. if (!_.has(result, key)) result[key] = 0;
  325. result[key]++;
  326. });
  327. };
  328. // Use a comparator function to figure out the smallest index at which
  329. // an object should be inserted so as to maintain order. Uses binary search.
  330. _.sortedIndex = function(array, obj, iterator, context) {
  331. iterator = iterator == null ? _.identity : lookupIterator(iterator);
  332. var value = iterator.call(context, obj);
  333. var low = 0, high = array.length;
  334. while (low < high) {
  335. var mid = (low + high) >>> 1;
  336. iterator.call(context, array[mid]) < value ? low = mid + 1 : high = mid;
  337. }
  338. return low;
  339. };
  340. // Safely convert anything iterable into a real, live array.
  341. _.toArray = function(obj) {
  342. if (!obj) return [];
  343. if (_.isArray(obj)) return slice.call(obj);
  344. if (obj.length === +obj.length) return _.map(obj, _.identity);
  345. return _.values(obj);
  346. };
  347. // Return the number of elements in an object.
  348. _.size = function(obj) {
  349. if (obj == null) return 0;
  350. return (obj.length === +obj.length) ? obj.length : _.keys(obj).length;
  351. };
  352. // Array Functions
  353. // ---------------
  354. // Get the first element of an array. Passing **n** will return the first N
  355. // values in the array. Aliased as `head` and `take`. The **guard** check
  356. // allows it to work with `_.map`.
  357. _.first = _.head = _.take = function(array, n, guard) {
  358. if (array == null) return void 0;
  359. return (n != null) && !guard ? slice.call(array, 0, n) : array[0];
  360. };
  361. // Returns everything but the last entry of the array. Especially useful on
  362. // the arguments object. Passing **n** will return all the values in
  363. // the array, excluding the last N. The **guard** check allows it to work with
  364. // `_.map`.
  365. _.initial = function(array, n, guard) {
  366. return slice.call(array, 0, array.length - ((n == null) || guard ? 1 : n));
  367. };
  368. // Get the last element of an array. Passing **n** will return the last N
  369. // values in the array. The **guard** check allows it to work with `_.map`.
  370. _.last = function(array, n, guard) {
  371. if (array == null) return void 0;
  372. if ((n != null) && !guard) {
  373. return slice.call(array, Math.max(array.length - n, 0));
  374. } else {
  375. return array[array.length - 1];
  376. }
  377. };
  378. // Returns everything but the first entry of the array. Aliased as `tail` and `drop`.
  379. // Especially useful on the arguments object. Passing an **n** will return
  380. // the rest N values in the array. The **guard**
  381. // check allows it to work with `_.map`.
  382. _.rest = _.tail = _.drop = function(array, n, guard) {
  383. return slice.call(array, (n == null) || guard ? 1 : n);
  384. };
  385. // Trim out all falsy values from an array.
  386. _.compact = function(array) {
  387. return _.filter(array, _.identity);
  388. };
  389. // Internal implementation of a recursive `flatten` function.
  390. var flatten = function(input, shallow, output) {
  391. each(input, function(value) {
  392. if (_.isArray(value)) {
  393. shallow ? push.apply(output, value) : flatten(value, shallow, output);
  394. } else {
  395. output.push(value);
  396. }
  397. });
  398. return output;
  399. };
  400. // Return a completely flattened version of an array.
  401. _.flatten = function(array, shallow) {
  402. return flatten(array, shallow, []);
  403. };
  404. // Return a version of the array that does not contain the specified value(s).
  405. _.without = function(array) {
  406. return _.difference(array, slice.call(arguments, 1));
  407. };
  408. // Produce a duplicate-free version of the array. If the array has already
  409. // been sorted, you have the option of using a faster algorithm.
  410. // Aliased as `unique`.
  411. _.uniq = _.unique = function(array, isSorted, iterator, context) {
  412. if (_.isFunction(isSorted)) {
  413. context = iterator;
  414. iterator = isSorted;
  415. isSorted = false;
  416. }
  417. var initial = iterator ? _.map(array, iterator, context) : array;
  418. var results = [];
  419. var seen = [];
  420. each(initial, function(value, index) {
  421. if (isSorted ? (!index || seen[seen.length - 1] !== value) : !_.contains(seen, value)) {
  422. seen.push(value);
  423. results.push(array[index]);
  424. }
  425. });
  426. return results;
  427. };
  428. // Produce an array that contains the union: each distinct element from all of
  429. // the passed-in arrays.
  430. _.union = function() {
  431. return _.uniq(concat.apply(ArrayProto, arguments));
  432. };
  433. // Produce an array that contains every item shared between all the
  434. // passed-in arrays.
  435. _.intersection = function(array) {
  436. var rest = slice.call(arguments, 1);
  437. return _.filter(_.uniq(array), function(item) {
  438. return _.every(rest, function(other) {
  439. return _.indexOf(other, item) >= 0;
  440. });
  441. });
  442. };
  443. // Take the difference between one array and a number of other arrays.
  444. // Only the elements present in just the first array will remain.
  445. _.difference = function(array) {
  446. var rest = concat.apply(ArrayProto, slice.call(arguments, 1));
  447. return _.filter(array, function(value){ return !_.contains(rest, value); });
  448. };
  449. // Zip together multiple lists into a single array -- elements that share
  450. // an index go together.
  451. _.zip = function() {
  452. var args = slice.call(arguments);
  453. var length = _.max(_.pluck(args, 'length'));
  454. var results = new Array(length);
  455. for (var i = 0; i < length; i++) {
  456. results[i] = _.pluck(args, "" + i);
  457. }
  458. return results;
  459. };
  460. // Converts lists into objects. Pass either a single array of `[key, value]`
  461. // pairs, or two parallel arrays of the same length -- one of keys, and one of
  462. // the corresponding values.
  463. _.object = function(list, values) {
  464. if (list == null) return {};
  465. var result = {};
  466. for (var i = 0, l = list.length; i < l; i++) {
  467. if (values) {
  468. result[list[i]] = values[i];
  469. } else {
  470. result[list[i][0]] = list[i][1];
  471. }
  472. }
  473. return result;
  474. };
  475. // If the browser doesn't supply us with indexOf (I'm looking at you, **MSIE**),
  476. // we need this function. Return the position of the first occurrence of an
  477. // item in an array, or -1 if the item is not included in the array.
  478. // Delegates to **ECMAScript 5**'s native `indexOf` if available.
  479. // If the array is large and already in sort order, pass `true`
  480. // for **isSorted** to use binary search.
  481. _.indexOf = function(array, item, isSorted) {
  482. if (array == null) return -1;
  483. var i = 0, l = array.length;
  484. if (isSorted) {
  485. if (typeof isSorted == 'number') {
  486. i = (isSorted < 0 ? Math.max(0, l + isSorted) : isSorted);
  487. } else {
  488. i = _.sortedIndex(array, item);
  489. return array[i] === item ? i : -1;
  490. }
  491. }
  492. if (nativeIndexOf && array.indexOf === nativeIndexOf) return array.indexOf(item, isSorted);
  493. for (; i < l; i++) if (array[i] === item) return i;
  494. return -1;
  495. };
  496. // Delegates to **ECMAScript 5**'s native `lastIndexOf` if available.
  497. _.lastIndexOf = function(array, item, from) {
  498. if (array == null) return -1;
  499. var hasIndex = from != null;
  500. if (nativeLastIndexOf && array.lastIndexOf === nativeLastIndexOf) {
  501. return hasIndex ? array.lastIndexOf(item, from) : array.lastIndexOf(item);
  502. }
  503. var i = (hasIndex ? from : array.length);
  504. while (i--) if (array[i] === item) return i;
  505. return -1;
  506. };
  507. // Generate an integer Array containing an arithmetic progression. A port of
  508. // the native Python `range()` function. See
  509. // [the Python documentation](http://docs.python.org/library/functions.html#range).
  510. _.range = function(start, stop, step) {
  511. if (arguments.length <= 1) {
  512. stop = start || 0;
  513. start = 0;
  514. }
  515. step = arguments[2] || 1;
  516. var len = Math.max(Math.ceil((stop - start) / step), 0);
  517. var idx = 0;
  518. var range = new Array(len);
  519. while(idx < len) {
  520. range[idx++] = start;
  521. start += step;
  522. }
  523. return range;
  524. };
  525. // Function (ahem) Functions
  526. // ------------------
  527. // Create a function bound to a given object (assigning `this`, and arguments,
  528. // optionally). Delegates to **ECMAScript 5**'s native `Function.bind` if
  529. // available.
  530. _.bind = function(func, context) {
  531. if (func.bind === nativeBind && nativeBind) return nativeBind.apply(func, slice.call(arguments, 1));
  532. var args = slice.call(arguments, 2);
  533. return function() {
  534. return func.apply(context, args.concat(slice.call(arguments)));
  535. };
  536. };
  537. // Partially apply a function by creating a version that has had some of its
  538. // arguments pre-filled, without changing its dynamic `this` context.
  539. _.partial = function(func) {
  540. var args = slice.call(arguments, 1);
  541. return function() {
  542. return func.apply(this, args.concat(slice.call(arguments)));
  543. };
  544. };
  545. // Bind all of an object's methods to that object. Useful for ensuring that
  546. // all callbacks defined on an object belong to it.
  547. _.bindAll = function(obj) {
  548. var funcs = slice.call(arguments, 1);
  549. if (funcs.length === 0) funcs = _.functions(obj);
  550. each(funcs, function(f) { obj[f] = _.bind(obj[f], obj); });
  551. return obj;
  552. };
  553. // Memoize an expensive function by storing its results.
  554. _.memoize = function(func, hasher) {
  555. var memo = {};
  556. hasher || (hasher = _.identity);
  557. return function() {
  558. var key = hasher.apply(this, arguments);
  559. return _.has(memo, key) ? memo[key] : (memo[key] = func.apply(this, arguments));
  560. };
  561. };
  562. // Delays a function for the given number of milliseconds, and then calls
  563. // it with the arguments supplied.
  564. _.delay = function(func, wait) {
  565. var args = slice.call(arguments, 2);
  566. return setTimeout(function(){ return func.apply(null, args); }, wait);
  567. };
  568. // Defers a function, scheduling it to run after the current call stack has
  569. // cleared.
  570. _.defer = function(func) {
  571. return _.delay.apply(_, [func, 1].concat(slice.call(arguments, 1)));
  572. };
  573. // Returns a function, that, when invoked, will only be triggered at most once
  574. // during a given window of time.
  575. _.throttle = function(func, wait) {
  576. var context, args, timeout, result;
  577. var previous = 0;
  578. var later = function() {
  579. previous = new Date;
  580. timeout = null;
  581. result = func.apply(context, args);
  582. };
  583. return function() {
  584. var now = new Date;
  585. var remaining = wait - (now - previous);
  586. context = this;
  587. args = arguments;
  588. if (remaining <= 0) {
  589. clearTimeout(timeout);
  590. timeout = null;
  591. previous = now;
  592. result = func.apply(context, args);
  593. } else if (!timeout) {
  594. timeout = setTimeout(later, remaining);
  595. }
  596. return result;
  597. };
  598. };
  599. // Returns a function, that, as long as it continues to be invoked, will not
  600. // be triggered. The function will be called after it stops being called for
  601. // N milliseconds. If `immediate` is passed, trigger the function on the
  602. // leading edge, instead of the trailing.
  603. _.debounce = function(func, wait, immediate) {
  604. var timeout, result;
  605. return function() {
  606. var context = this, args = arguments;
  607. var later = function() {
  608. timeout = null;
  609. if (!immediate) result = func.apply(context, args);
  610. };
  611. var callNow = immediate && !timeout;
  612. clearTimeout(timeout);
  613. timeout = setTimeout(later, wait);
  614. if (callNow) result = func.apply(context, args);
  615. return result;
  616. };
  617. };
  618. // Returns a function that will be executed at most one time, no matter how
  619. // often you call it. Useful for lazy initialization.
  620. _.once = function(func) {
  621. var ran = false, memo;
  622. return function() {
  623. if (ran) return memo;
  624. ran = true;
  625. memo = func.apply(this, arguments);
  626. func = null;
  627. return memo;
  628. };
  629. };
  630. // Returns the first function passed as an argument to the second,
  631. // allowing you to adjust arguments, run code before and after, and
  632. // conditionally execute the original function.
  633. _.wrap = function(func, wrapper) {
  634. return function() {
  635. var args = [func];
  636. push.apply(args, arguments);
  637. return wrapper.apply(this, args);
  638. };
  639. };
  640. // Returns a function that is the composition of a list of functions, each
  641. // consuming the return value of the function that follows.
  642. _.compose = function() {
  643. var funcs = arguments;
  644. return function() {
  645. var args = arguments;
  646. for (var i = funcs.length - 1; i >= 0; i--) {
  647. args = [funcs[i].apply(this, args)];
  648. }
  649. return args[0];
  650. };
  651. };
  652. // Returns a function that will only be executed after being called N times.
  653. _.after = function(times, func) {
  654. if (times <= 0) return func();
  655. return function() {
  656. if (--times < 1) {
  657. return func.apply(this, arguments);
  658. }
  659. };
  660. };
  661. // Object Functions
  662. // ----------------
  663. // Retrieve the names of an object's properties.
  664. // Delegates to **ECMAScript 5**'s native `Object.keys`
  665. _.keys = nativeKeys || function(obj) {
  666. if (obj !== Object(obj)) throw new TypeError('Invalid object');
  667. var keys = [];
  668. for (var key in obj) if (_.has(obj, key)) keys[keys.length] = key;
  669. return keys;
  670. };
  671. // Retrieve the values of an object's properties.
  672. _.values = function(obj) {
  673. var values = [];
  674. for (var key in obj) if (_.has(obj, key)) values.push(obj[key]);
  675. return values;
  676. };
  677. // Convert an object into a list of `[key, value]` pairs.
  678. _.pairs = function(obj) {
  679. var pairs = [];
  680. for (var key in obj) if (_.has(obj, key)) pairs.push([key, obj[key]]);
  681. return pairs;
  682. };
  683. // Invert the keys and values of an object. The values must be serializable.
  684. _.invert = function(obj) {
  685. var result = {};
  686. for (var key in obj) if (_.has(obj, key)) result[obj[key]] = key;
  687. return result;
  688. };
  689. // Return a sorted list of the function names available on the object.
  690. // Aliased as `methods`
  691. _.functions = _.methods = function(obj) {
  692. var names = [];
  693. for (var key in obj) {
  694. if (_.isFunction(obj[key])) names.push(key);
  695. }
  696. return names.sort();
  697. };
  698. // Extend a given object with all the properties in passed-in object(s).
  699. _.extend = function(obj) {
  700. each(slice.call(arguments, 1), function(source) {
  701. if (source) {
  702. for (var prop in source) {
  703. obj[prop] = source[prop];
  704. }
  705. }
  706. });
  707. return obj;
  708. };
  709. // Return a copy of the object only containing the whitelisted properties.
  710. _.pick = function(obj) {
  711. var copy = {};
  712. var keys = concat.apply(ArrayProto, slice.call(arguments, 1));
  713. each(keys, function(key) {
  714. if (key in obj) copy[key] = obj[key];
  715. });
  716. return copy;
  717. };
  718. // Return a copy of the object without the blacklisted properties.
  719. _.omit = function(obj) {
  720. var copy = {};
  721. var keys = concat.apply(ArrayProto, slice.call(arguments, 1));
  722. for (var key in obj) {
  723. if (!_.contains(keys, key)) copy[key] = obj[key];
  724. }
  725. return copy;
  726. };
  727. // Fill in a given object with default properties.
  728. _.defaults = function(obj) {
  729. each(slice.call(arguments, 1), function(source) {
  730. if (source) {
  731. for (var prop in source) {
  732. if (obj[prop] == null) obj[prop] = source[prop];
  733. }
  734. }
  735. });
  736. return obj;
  737. };
  738. // Create a (shallow-cloned) duplicate of an object.
  739. _.clone = function(obj) {
  740. if (!_.isObject(obj)) return obj;
  741. return _.isArray(obj) ? obj.slice() : _.extend({}, obj);
  742. };
  743. // Invokes interceptor with the obj, and then returns obj.
  744. // The primary purpose of this method is to "tap into" a method chain, in
  745. // order to perform operations on intermediate results within the chain.
  746. _.tap = function(obj, interceptor) {
  747. interceptor(obj);
  748. return obj;
  749. };
  750. // Internal recursive comparison function for `isEqual`.
  751. var eq = function(a, b, aStack, bStack) {
  752. // Identical objects are equal. `0 === -0`, but they aren't identical.
  753. // See the Harmony `egal` proposal: http://wiki.ecmascript.org/doku.php?id=harmony:egal.
  754. if (a === b) return a !== 0 || 1 / a == 1 / b;
  755. // A strict comparison is necessary because `null == undefined`.
  756. if (a == null || b == null) return a === b;
  757. // Unwrap any wrapped objects.
  758. if (a instanceof _) a = a._wrapped;
  759. if (b instanceof _) b = b._wrapped;
  760. // Compare `[[Class]]` names.
  761. var className = toString.call(a);
  762. if (className != toString.call(b)) return false;
  763. switch (className) {
  764. // Strings, numbers, dates, and booleans are compared by value.
  765. case '[object String]':
  766. // Primitives and their corresponding object wrappers are equivalent; thus, `"5"` is
  767. // equivalent to `new String("5")`.
  768. return a == String(b);
  769. case '[object Number]':
  770. // `NaN`s are equivalent, but non-reflexive. An `egal` comparison is performed for
  771. // other numeric values.
  772. return a != +a ? b != +b : (a == 0 ? 1 / a == 1 / b : a == +b);
  773. case '[object Date]':
  774. case '[object Boolean]':
  775. // Coerce dates and booleans to numeric primitive values. Dates are compared by their
  776. // millisecond representations. Note that invalid dates with millisecond representations
  777. // of `NaN` are not equivalent.
  778. return +a == +b;
  779. // RegExps are compared by their source patterns and flags.
  780. case '[object RegExp]':
  781. return a.source == b.source &&
  782. a.global == b.global &&
  783. a.multiline == b.multiline &&
  784. a.ignoreCase == b.ignoreCase;
  785. }
  786. if (typeof a != 'object' || typeof b != 'object') return false;
  787. // Assume equality for cyclic structures. The algorithm for detecting cyclic
  788. // structures is adapted from ES 5.1 section 15.12.3, abstract operation `JO`.
  789. var length = aStack.length;
  790. while (length--) {
  791. // Linear search. Performance is inversely proportional to the number of
  792. // unique nested structures.
  793. if (aStack[length] == a) return bStack[length] == b;
  794. }
  795. // Add the first object to the stack of traversed objects.
  796. aStack.push(a);
  797. bStack.push(b);
  798. var size = 0, result = true;
  799. // Recursively compare objects and arrays.
  800. if (className == '[object Array]') {
  801. // Compare array lengths to determine if a deep comparison is necessary.
  802. size = a.length;
  803. result = size == b.length;
  804. if (result) {
  805. // Deep compare the contents, ignoring non-numeric properties.
  806. while (size--) {
  807. if (!(result = eq(a[size], b[size], aStack, bStack))) break;
  808. }
  809. }
  810. } else {
  811. // Objects with different constructors are not equivalent, but `Object`s
  812. // from different frames are.
  813. var aCtor = a.constructor, bCtor = b.constructor;
  814. if (aCtor !== bCtor && !(_.isFunction(aCtor) && (aCtor instanceof aCtor) &&
  815. _.isFunction(bCtor) && (bCtor instanceof bCtor))) {
  816. return false;
  817. }
  818. // Deep compare objects.
  819. for (var key in a) {
  820. if (_.has(a, key)) {
  821. // Count the expected number of properties.
  822. size++;
  823. // Deep compare each member.
  824. if (!(result = _.has(b, key) && eq(a[key], b[key], aStack, bStack))) break;
  825. }
  826. }
  827. // Ensure that both objects contain the same number of properties.
  828. if (result) {
  829. for (key in b) {
  830. if (_.has(b, key) && !(size--)) break;
  831. }
  832. result = !size;
  833. }
  834. }
  835. // Remove the first object from the stack of traversed objects.
  836. aStack.pop();
  837. bStack.pop();
  838. return result;
  839. };
  840. // Perform a deep comparison to check if two objects are equal.
  841. _.isEqual = function(a, b) {
  842. return eq(a, b, [], []);
  843. };
  844. // Is a given array, string, or object empty?
  845. // An "empty" object has no enumerable own-properties.
  846. _.isEmpty = function(obj) {
  847. if (obj == null) return true;
  848. if (_.isArray(obj) || _.isString(obj)) return obj.length === 0;
  849. for (var key in obj) if (_.has(obj, key)) return false;
  850. return true;
  851. };
  852. // Is a given value a DOM element?
  853. _.isElement = function(obj) {
  854. return !!(obj && obj.nodeType === 1);
  855. };
  856. // Is a given value an array?
  857. // Delegates to ECMA5's native Array.isArray
  858. _.isArray = nativeIsArray || function(obj) {
  859. return toString.call(obj) == '[object Array]';
  860. };
  861. // Is a given variable an object?
  862. _.isObject = function(obj) {
  863. return obj === Object(obj);
  864. };
  865. // Add some isType methods: isArguments, isFunction, isString, isNumber, isDate, isRegExp.
  866. each(['Arguments', 'Function', 'String', 'Number', 'Date', 'RegExp'], function(name) {
  867. _['is' + name] = function(obj) {
  868. return toString.call(obj) == '[object ' + name + ']';
  869. };
  870. });
  871. // Define a fallback version of the method in browsers (ahem, IE), where
  872. // there isn't any inspectable "Arguments" type.
  873. if (!_.isArguments(arguments)) {
  874. _.isArguments = function(obj) {
  875. return !!(obj && _.has(obj, 'callee'));
  876. };
  877. }
  878. // Optimize `isFunction` if appropriate.
  879. if (typeof (/./) !== 'function') {
  880. _.isFunction = function(obj) {
  881. return typeof obj === 'function';
  882. };
  883. }
  884. // Is a given object a finite number?
  885. _.isFinite = function(obj) {
  886. return isFinite(obj) && !isNaN(parseFloat(obj));
  887. };
  888. // Is the given value `NaN`? (NaN is the only number which does not equal itself).
  889. _.isNaN = function(obj) {
  890. return _.isNumber(obj) && obj != +obj;
  891. };
  892. // Is a given value a boolean?
  893. _.isBoolean = function(obj) {
  894. return obj === true || obj === false || toString.call(obj) == '[object Boolean]';
  895. };
  896. // Is a given value equal to null?
  897. _.isNull = function(obj) {
  898. return obj === null;
  899. };
  900. // Is a given variable undefined?
  901. _.isUndefined = function(obj) {
  902. return obj === void 0;
  903. };
  904. // Shortcut function for checking if an object has a given property directly
  905. // on itself (in other words, not on a prototype).
  906. _.has = function(obj, key) {
  907. return hasOwnProperty.call(obj, key);
  908. };
  909. // Utility Functions
  910. // -----------------
  911. // Run Underscore.js in *noConflict* mode, returning the `_` variable to its
  912. // previous owner. Returns a reference to the Underscore object.
  913. _.noConflict = function() {
  914. root._ = previousUnderscore;
  915. return this;
  916. };
  917. // Keep the identity function around for default iterators.
  918. _.identity = function(value) {
  919. return value;
  920. };
  921. // Run a function **n** times.
  922. _.times = function(n, iterator, context) {
  923. var accum = Array(n);
  924. for (var i = 0; i < n; i++) accum[i] = iterator.call(context, i);
  925. return accum;
  926. };
  927. // Return a random integer between min and max (inclusive).
  928. _.random = function(min, max) {
  929. if (max == null) {
  930. max = min;
  931. min = 0;
  932. }
  933. return min + Math.floor(Math.random() * (max - min + 1));
  934. };
  935. // List of HTML entities for escaping.
  936. var entityMap = {
  937. escape: {
  938. '&': '&amp;',
  939. '<': '&lt;',
  940. '>': '&gt;',
  941. '"': '&quot;',
  942. "'": '&#x27;',
  943. '/': '&#x2F;'
  944. }
  945. };
  946. entityMap.unescape = _.invert(entityMap.escape);
  947. // Regexes containing the keys and values listed immediately above.
  948. var entityRegexes = {
  949. escape: new RegExp('[' + _.keys(entityMap.escape).join('') + ']', 'g'),
  950. unescape: new RegExp('(' + _.keys(entityMap.unescape).join('|') + ')', 'g')
  951. };
  952. // Functions for escaping and unescaping strings to/from HTML interpolation.
  953. _.each(['escape', 'unescape'], function(method) {
  954. _[method] = function(string) {
  955. if (string == null) return '';
  956. return ('' + string).replace(entityRegexes[method], function(match) {
  957. return entityMap[method][match];
  958. });
  959. };
  960. });
  961. // If the value of the named property is a function then invoke it;
  962. // otherwise, return it.
  963. _.result = function(object, property) {
  964. if (object == null) return null;
  965. var value = object[property];
  966. return _.isFunction(value) ? value.call(object) : value;
  967. };
  968. // Add your own custom functions to the Underscore object.
  969. _.mixin = function(obj) {
  970. each(_.functions(obj), function(name){
  971. var func = _[name] = obj[name];
  972. _.prototype[name] = function() {
  973. var args = [this._wrapped];
  974. push.apply(args, arguments);
  975. return result.call(this, func.apply(_, args));
  976. };
  977. });
  978. };
  979. // Generate a unique integer id (unique within the entire client session).
  980. // Useful for temporary DOM ids.
  981. var idCounter = 0;
  982. _.uniqueId = function(prefix) {
  983. var id = ++idCounter + '';
  984. return prefix ? prefix + id : id;
  985. };
  986. // By default, Underscore uses ERB-style template delimiters, change the
  987. // following template settings to use alternative delimiters.
  988. _.templateSettings = {
  989. evaluate : /<%([\s\S]+?)%>/g,
  990. interpolate : /<%=([\s\S]+?)%>/g,
  991. escape : /<%-([\s\S]+?)%>/g
  992. };
  993. // When customizing `templateSettings`, if you don't want to define an
  994. // interpolation, evaluation or escaping regex, we need one that is
  995. // guaranteed not to match.
  996. var noMatch = /(.)^/;
  997. // Certain characters need to be escaped so that they can be put into a
  998. // string literal.
  999. var escapes = {
  1000. "'": "'",
  1001. '\\': '\\',
  1002. '\r': 'r',
  1003. '\n': 'n',
  1004. '\t': 't',
  1005. '\u2028': 'u2028',
  1006. '\u2029': 'u2029'
  1007. };
  1008. var escaper = /\\|'|\r|\n|\t|\u2028|\u2029/g;
  1009. // JavaScript micro-templating, similar to John Resig's implementation.
  1010. // Underscore templating handles arbitrary delimiters, preserves whitespace,
  1011. // and correctly escapes quotes within interpolated code.
  1012. _.template = function(text, data, settings) {
  1013. var render;
  1014. settings = _.defaults({}, settings, _.templateSettings);
  1015. // Combine delimiters into one regular expression via alternation.
  1016. var matcher = new RegExp([
  1017. (settings.escape || noMatch).source,
  1018. (settings.interpolate || noMatch).source,
  1019. (settings.evaluate || noMatch).source
  1020. ].join('|') + '|$', 'g');
  1021. // Compile the template source, escaping string literals appropriately.
  1022. var index = 0;
  1023. var source = "__p+='";
  1024. text.replace(matcher, function(match, escape, interpolate, evaluate, offset) {
  1025. source += text.slice(index, offset)
  1026. .replace(escaper, function(match) { return '\\' + escapes[match]; });
  1027. if (escape) {
  1028. source += "'+\n((__t=(" + escape + "))==null?'':_.escape(__t))+\n'";
  1029. }
  1030. if (interpolate) {
  1031. source += "'+\n((__t=(" + interpolate + "))==null?'':__t)+\n'";
  1032. }
  1033. if (evaluate) {
  1034. source += "';\n" + evaluate + "\n__p+='";
  1035. }
  1036. index = offset + match.length;
  1037. return match;
  1038. });
  1039. source += "';\n";
  1040. // If a variable is not specified, place data values in local scope.
  1041. if (!settings.variable) source = 'with(obj||{}){\n' + source + '}\n';
  1042. source = "var __t,__p='',__j=Array.prototype.join," +
  1043. "print=function(){__p+=__j.call(arguments,'');};\n" +
  1044. source + "return __p;\n";
  1045. try {
  1046. render = new Function(settings.variable || 'obj', '_', source);
  1047. } catch (e) {
  1048. e.source = source;
  1049. throw e;
  1050. }
  1051. if (data) return render(data, _);
  1052. var template = function(data) {
  1053. return render.call(this, data, _);
  1054. };
  1055. // Provide the compiled function source as a convenience for precompilation.
  1056. template.source = 'function(' + (settings.variable || 'obj') + '){\n' + source + '}';
  1057. return template;
  1058. };
  1059. // Add a "chain" function, which will delegate to the wrapper.
  1060. _.chain = function(obj) {
  1061. return _(obj).chain();
  1062. };
  1063. // OOP
  1064. // ---------------
  1065. // If Underscore is called as a function, it returns a wrapped object that
  1066. // can be used OO-style. This wrapper holds altered versions of all the
  1067. // underscore functions. Wrapped objects may be chained.
  1068. // Helper function to continue chaining intermediate results.
  1069. var result = function(obj) {
  1070. return this._chain ? _(obj).chain() : obj;
  1071. };
  1072. // Add all of the Underscore functions to the wrapper object.
  1073. _.mixin(_);
  1074. // Add all mutator Array functions to the wrapper.
  1075. each(['pop', 'push', 'reverse', 'shift', 'sort', 'splice', 'unshift'], function(name) {
  1076. var method = ArrayProto[name];
  1077. _.prototype[name] = function() {
  1078. var obj = this._wrapped;
  1079. method.apply(obj, arguments);
  1080. if ((name == 'shift' || name == 'splice') && obj.length === 0) delete obj[0];
  1081. return result.call(this, obj);
  1082. };
  1083. });
  1084. // Add all accessor Array functions to the wrapper.
  1085. each(['concat', 'join', 'slice'], function(name) {
  1086. var method = ArrayProto[name];
  1087. _.prototype[name] = function() {
  1088. return result.call(this, method.apply(this._wrapped, arguments));
  1089. };
  1090. });
  1091. _.extend(_.prototype, {
  1092. // Start chaining a wrapped Underscore object.
  1093. chain: function() {
  1094. this._chain = true;
  1095. return this;
  1096. },
  1097. // Extracts the result from a wrapped and chained object.
  1098. value: function() {
  1099. return this._wrapped;
  1100. }
  1101. });
  1102. }).call(this);
  1103. },
  1104. {}],
  1105. 2:[function(req,module,exports){
  1106. "use strict";
  1107. var _ = req("underscore");
  1108. var errors = {
  1109. // JSHint options
  1110. E001: "Bad option: '{a}'.",
  1111. E002: "Bad option value.",
  1112. // JSHint input
  1113. E003: "Expected a JSON value.",
  1114. E004: "Input is neither a string nor an array of strings.",
  1115. E005: "Input is empty.",
  1116. E006: "Unexpected early end of program.",
  1117. // Strict mode
  1118. E007: "Missing \"use strict\" statement.",
  1119. E008: "Strict violation.",
  1120. E009: "Option 'validthis' can't be used in a global scope.",
  1121. E010: "'with' is not allowed in strict mode.",
  1122. // Constants
  1123. E011: "const '{a}' has already been declared.",
  1124. E012: "const '{a}' is initialized to 'undefined'.",
  1125. E013: "Attempting to override '{a}' which is a constant.",
  1126. // Regular expressions
  1127. E014: "A regular expression literal can be confused with '/='.",
  1128. E015: "Unclosed regular expression.",
  1129. E016: "Invalid regular expression.",
  1130. // Tokens
  1131. E017: "Unclosed comment.",
  1132. E018: "Unbegun comment.",
  1133. E019: "Unmatched '{a}'.",
  1134. E020: "Expected '{a}' to match '{b}' from line {c} and instead saw '{d}'.",
  1135. E021: "Expected '{a}' and instead saw '{b}'.",
  1136. E022: "Line breaking error '{a}'.",
  1137. E023: "Missing '{a}'.",
  1138. E024: "Unexpected '{a}'.",
  1139. E025: "Missing ':' on a case clause.",
  1140. E026: "Missing '}' to match '{' from line {a}.",
  1141. E027: "Missing ']' to match '[' form line {a}.",
  1142. E028: "Illegal comma.",
  1143. E029: "Unclosed string.",
  1144. // Everything else
  1145. E030: "Expected an identifier and instead saw '{a}'.",
  1146. E031: "Bad assignment.", // FIXME: Rephrase
  1147. E032: "Expected a small integer or 'false' and instead saw '{a}'.",
  1148. E033: "Expected an operator and instead saw '{a}'.",
  1149. E034: "get/set are ES5 features.",
  1150. E035: "Missing property name.",
  1151. E036: "Expected to see a statement and instead saw a block.",
  1152. E037: null, // Vacant
  1153. E038: null, // Vacant
  1154. E039: "Function declarations are not invocable. Wrap the whole function invocation in parens.",
  1155. E040: "Each value should have its own case label.",
  1156. E041: "Unrecoverable syntax error.",
  1157. E042: "Stopping.",
  1158. E043: "Too many errors.",
  1159. E044: "'{a}' is already defined and can't be redefined.",
  1160. E045: "Invalid for each loop.",
  1161. E046: "A yield statement shall be within a generator function (with syntax: `function*`)",
  1162. E047: "A generator function shall contain a yield statement.",
  1163. E048: "Let declaration not directly within block.",
  1164. E049: "A {a} cannot be named '{b}'.",
  1165. E050: "Mozilla requires the yield expression to be parenthesized here.",
  1166. E051: "Regular parameters cannot come after default parameters."
  1167. };
  1168. var warnings = {
  1169. W001: "'hasOwnProperty' is a really bad name.",
  1170. W002: "Value of '{a}' may be overwritten in IE 8 and earlier.",
  1171. W003: "'{a}' was used before it was defined.",
  1172. W004: "'{a}' is already defined.",
  1173. W005: "A dot following a number can be confused with a decimal point.",
  1174. W006: "Confusing minuses.",
  1175. W007: "Confusing pluses.",
  1176. W008: "A leading decimal point can be confused with a dot: '{a}'.",
  1177. W009: "The array literal notation [] is preferrable.",
  1178. W010: "The object literal notation {} is preferrable.",
  1179. W011: "Unexpected space after '{a}'.",
  1180. W012: "Unexpected space before '{a}'.",
  1181. W013: "Missing space after '{a}'.",
  1182. W014: "Bad line breaking before '{a}'.",
  1183. W015: "Expected '{a}' to have an indentation at {b} instead at {c}.",
  1184. W016: "Unexpected use of '{a}'.",
  1185. W017: "Bad operand.",
  1186. W018: "Confusing use of '{a}'.",
  1187. W019: "Use the isNaN function to compare with NaN.",
  1188. W020: "Read only.",
  1189. W021: "'{a}' is a function.",
  1190. W022: "Do not assign to the exception parameter.",
  1191. W023: "Expected an identifier in an assignment and instead saw a function invocation.",
  1192. W024: "Expected an identifier and instead saw '{a}' (a reserved word).",
  1193. W025: "Missing name in function declaration.",
  1194. W026: "Inner functions should be listed at the top of the outer function.",
  1195. W027: "Unreachable '{a}' after '{b}'.",
  1196. W028: "Label '{a}' on {b} statement.",
  1197. W030: "Expected an assignment or function call and instead saw an expression.",
  1198. W031: "Do not use 'new' for side effects.",
  1199. W032: "Unnecessary semicolon.",
  1200. W033: "Missing semicolon.",
  1201. W034: "Unnecessary directive \"{a}\".",
  1202. W035: "Empty block.",
  1203. W036: "Unexpected /*member '{a}'.",
  1204. W037: "'{a}' is a statement label.",
  1205. W038: "'{a}' used out of scope.",
  1206. W039: "'{a}' is not allowed.",
  1207. W040: "Possible strict violation.",
  1208. W041: "Use '{a}' to compare with '{b}'.",
  1209. W042: "Avoid EOL escaping.",
  1210. W043: "Bad escaping of EOL. Use option multistr if needed.",
  1211. W044: "Bad or unnecessary escaping.",
  1212. W045: "Bad number '{a}'.",
  1213. W046: "Don't use extra leading zeros '{a}'.",
  1214. W047: "A trailing decimal point can be confused with a dot: '{a}'.",
  1215. W048: "Unexpected control character in regular expression.",
  1216. W049: "Unexpected escaped character '{a}' in regular expression.",
  1217. W050: "JavaScript URL.",
  1218. W051: "Variables should not be deleted.",
  1219. W052: "Unexpected '{a}'.",
  1220. W053: "Do not use {a} as a constructor.",
  1221. W054: "The Function constructor is a form of eval.",
  1222. W055: "A constructor name should start with an uppercase letter.",
  1223. W056: "Bad constructor.",
  1224. W057: "Weird construction. Is 'new' unnecessary?",
  1225. W058: "Missing '()' invoking a constructor.",
  1226. W059: "Avoid arguments.{a}.",
  1227. W060: "document.write can be a form of eval.",
  1228. W061: "eval can be harmful.",
  1229. W062: "Wrap an immediate function invocation in parens " +
  1230. "to assist the reader in understanding that the expression " +
  1231. "is the result of a function, and not the function itself.",
  1232. W063: "Math is not a function.",
  1233. W064: "Missing 'new' prefix when invoking a constructor.",
  1234. W065: "Missing radix parameter.",
  1235. W066: "Implied eval. Consider passing a function instead of a string.",
  1236. W067: "Bad invocation.",
  1237. W068: "Wrapping non-IIFE function literals in parens is unnecessary.",
  1238. W069: "['{a}'] is better written in dot notation.",
  1239. W070: "Extra comma. (it breaks older versions of IE)",
  1240. W071: "This function has too many statements. ({a})",
  1241. W072: "This function has too many parameters. ({a})",
  1242. W073: "Blocks are nested too deeply. ({a})",
  1243. W074: "This function's cyclomatic complexity is too high. ({a})",
  1244. W075: "Duplicate key '{a}'.",
  1245. W076: "Unexpected parameter '{a}' in get {b} function.",
  1246. W077: "Expected a single parameter in set {a} function.",
  1247. W078: "Setter is defined without getter.",
  1248. W079: "Redefinition of '{a}'.",
  1249. W080: "It's not necessary to initialize '{a}' to 'undefined'.",
  1250. W081: "Too many var statements.",
  1251. W082: "Function declarations should not be placed in blocks. " +
  1252. "Use a function expression or move the statement to the top of " +
  1253. "the outer function.",
  1254. W083: "Don't make functions within a loop.",
  1255. W084: "Assignment in conditional expression",
  1256. W085: "Don't use 'with'.",
  1257. W086: "Expected a 'break' statement before '{a}'.",
  1258. W087: "Forgotten 'debugger' statement?",
  1259. W088: "Creating global 'for' variable. Should be 'for (var {a} ...'.",
  1260. W089: "The body of a for in should be wrapped in an if statement to filter " +
  1261. "unwanted properties from the prototype.",
  1262. W090: "'{a}' is not a statement label.",
  1263. W091: "'{a}' is out of scope.",
  1264. W092: "Wrap the /regexp/ literal in parens to disambiguate the slash operator.",
  1265. W093: "Did you mean to return a conditional instead of an assignment?",
  1266. W094: "Unexpected comma.",
  1267. W095: "Expected a string and instead saw {a}.",
  1268. W096: "The '{a}' key may produce unexpected results.",
  1269. W097: "Use the function form of \"use strict\".",
  1270. W098: "'{a}' is defined but never used.",
  1271. W099: "Mixed spaces and tabs.",
  1272. W100: "This character may get silently deleted by one or more browsers.",
  1273. W101: "Line is too long.",
  1274. W102: "Trailing whitespace.",
  1275. W103: "The '{a}' property is deprecated.",
  1276. W104: "'{a}' is only available in JavaScript 1.7.",
  1277. W105: "Unexpected {a} in '{b}'.",
  1278. W106: "Identifier '{a}' is not in camel case.",
  1279. W107: "Script URL.",
  1280. W108: "Strings must use doublequote.",
  1281. W109: "Strings must use singlequote.",
  1282. W110: "Mixed double and single quotes.",
  1283. W112: "Unclosed string.",
  1284. W113: "Control character in string: {a}.",
  1285. W114: "Avoid {a}.",
  1286. W115: "Octal literals are not allowed in strict mode.",
  1287. W116: "Expected '{a}' and instead saw '{b}'.",
  1288. W117: "'{a}' is not defined.",
  1289. W118: "'{a}' is only available in Mozilla JavaScript extensions (use moz option).",
  1290. W119: "'{a}' is only available in ES6 (use esnext option).",
  1291. W120: "You might be leaking a variable ({a}) here."
  1292. };
  1293. var info = {
  1294. I001: "Comma warnings can be turned off with 'laxcomma'.",
  1295. I002: "Reserved words as properties can be used under the 'es5' option.",
  1296. I003: "ES5 option is now set per default"
  1297. };
  1298. exports.errors = {};
  1299. exports.warnings = {};
  1300. exports.info = {};
  1301. _.each(errors, function (desc, code) {
  1302. exports.errors[code] = { code: code, desc: desc };
  1303. });
  1304. _.each(warnings, function (desc, code) {
  1305. exports.warnings[code] = { code: code, desc: desc };
  1306. });
  1307. _.each(info, function (desc, code) {
  1308. exports.info[code] = { code: code, desc: desc };
  1309. });
  1310. },
  1311. {"underscore":1}],
  1312. 3:[function(req,module,exports){
  1313. // jshint -W001
  1314. "use strict";
  1315. // Identifiers provided by the ECMAScript standard.
  1316. exports.reservedVars = {
  1317. arguments : false,
  1318. NaN : false
  1319. };
  1320. exports.ecmaIdentifiers = {
  1321. Array : false,
  1322. Boolean : false,
  1323. Date : false,
  1324. decodeURI : false,
  1325. decodeURIComponent : false,
  1326. encodeURI : false,
  1327. encodeURIComponent : false,
  1328. Error : false,
  1329. "eval" : false,
  1330. EvalError : false,
  1331. Function : false,
  1332. hasOwnProperty : false,
  1333. isFinite : false,
  1334. isNaN : false,
  1335. JSON : false,
  1336. Math : false,
  1337. Map : false,
  1338. Number : false,
  1339. Object : false,
  1340. parseInt : false,
  1341. parseFloat : false,
  1342. RangeError : false,
  1343. ReferenceError : false,
  1344. RegExp : false,
  1345. Set : false,
  1346. String : false,
  1347. SyntaxError : false,
  1348. TypeError : false,
  1349. URIError : false,
  1350. WeakMap : false
  1351. };
  1352. // Global variables commonly provided by a web browser environment.
  1353. exports.browser = {
  1354. ArrayBuffer : false,
  1355. ArrayBufferView : false,
  1356. Audio : false,
  1357. Blob : false,
  1358. addEventListener : false,
  1359. applicationCache : false,
  1360. atob : false,
  1361. blur : false,
  1362. btoa : false,
  1363. clearInterval : false,
  1364. clearTimeout : false,
  1365. close : false,
  1366. closed : false,
  1367. CustomEvent : false,
  1368. DataView : false,
  1369. DOMParser : false,
  1370. defaultStatus : false,
  1371. document : false,
  1372. Element : false,
  1373. ElementTimeControl : false,
  1374. event : false,
  1375. FileReader : false,
  1376. Float32Array : false,
  1377. Float64Array : false,
  1378. FormData : false,
  1379. focus : false,
  1380. frames : false,
  1381. getComputedStyle : false,
  1382. HTMLElement : false,
  1383. HTMLAnchorElement : false,
  1384. HTMLBaseElement : false,
  1385. HTMLBlockquoteElement: false,
  1386. HTMLBodyElement : false,
  1387. HTMLBRElement : false,
  1388. HTMLButtonElement : false,
  1389. HTMLCanvasElement : false,
  1390. HTMLDirectoryElement : false,
  1391. HTMLDivElement : false,
  1392. HTMLDListElement : false,
  1393. HTMLFieldSetElement : false,
  1394. HTMLFontElement : false,
  1395. HTMLFormElement : false,
  1396. HTMLFrameElement : false,
  1397. HTMLFrameSetElement : false,
  1398. HTMLHeadElement : false,
  1399. HTMLHeadingElement : false,
  1400. HTMLHRElement : false,
  1401. HTMLHtmlElement : false,
  1402. HTMLIFrameElement : false,
  1403. HTMLImageElement : false,
  1404. HTMLInputElement : false,
  1405. HTMLIsIndexElement : false,
  1406. HTMLLabelElement : false,
  1407. HTMLLayerElement : false,
  1408. HTMLLegendElement : false,
  1409. HTMLLIElement : false,
  1410. HTMLLinkElement : false,
  1411. HTMLMapElement : false,
  1412. HTMLMenuElement : false,
  1413. HTMLMetaElement : false,
  1414. HTMLModElement : false,
  1415. HTMLObjectElement : false,
  1416. HTMLOListElement : false,
  1417. HTMLOptGroupElement : false,
  1418. HTMLOptionElement : false,
  1419. HTMLParagraphElement : false,
  1420. HTMLParamElement : false,
  1421. HTMLPreElement : false,
  1422. HTMLQuoteElement : false,
  1423. HTMLScriptElement : false,
  1424. HTMLSelectElement : false,
  1425. HTMLStyleElement : false,
  1426. HTMLTableCaptionElement: false,
  1427. HTMLTableCellElement : false,
  1428. HTMLTableColElement : false,
  1429. HTMLTableElement : false,
  1430. HTMLTableRowElement : false,
  1431. HTMLTableSectionElement: false,
  1432. HTMLTextAreaElement : false,
  1433. HTMLTitleElement : false,
  1434. HTMLUListElement : false,
  1435. HTMLVideoElement : false,
  1436. history : false,
  1437. Int16Array : false,
  1438. Int32Array : false,
  1439. Int8Array : false,
  1440. Image : false,
  1441. length : false,
  1442. localStorage : false,
  1443. location : false,
  1444. MessageChannel : false,
  1445. MessageEvent : false,
  1446. MessagePort : false,
  1447. MouseEvent : false,
  1448. moveBy : false,
  1449. moveTo : false,
  1450. MutationObserver : false,
  1451. name : false,
  1452. Node : false,
  1453. NodeFilter : false,
  1454. navigator : false,
  1455. onbeforeunload : true,
  1456. onblur : true,
  1457. onerror : true,
  1458. onfocus : true,
  1459. onload : true,
  1460. onresize : true,
  1461. onunload : true,
  1462. open : false,
  1463. openDatabase : false,
  1464. opener : false,
  1465. Option : false,
  1466. parent : false,
  1467. print : false,
  1468. removeEventListener : false,
  1469. resizeBy : false,
  1470. resizeTo : false,
  1471. screen : false,
  1472. scroll : false,
  1473. scrollBy : false,
  1474. scrollTo : false,
  1475. sessionStorage : false,
  1476. setInterval : false,
  1477. setTimeout : false,
  1478. SharedWorker : false,
  1479. status : false,
  1480. SVGAElement : false,
  1481. SVGAltGlyphDefElement: false,
  1482. SVGAltGlyphElement : false,
  1483. SVGAltGlyphItemElement: false,
  1484. SVGAngle : false,
  1485. SVGAnimateColorElement: false,
  1486. SVGAnimateElement : false,
  1487. SVGAnimateMotionElement: false,
  1488. SVGAnimateTransformElement: false,
  1489. SVGAnimatedAngle : false,
  1490. SVGAnimatedBoolean : false,
  1491. SVGAnimatedEnumeration: false,
  1492. SVGAnimatedInteger : false,
  1493. SVGAnimatedLength : false,
  1494. SVGAnimatedLengthList: false,
  1495. SVGAnimatedNumber : false,
  1496. SVGAnimatedNumberList: false,
  1497. SVGAnimatedPathData : false,
  1498. SVGAnimatedPoints : false,
  1499. SVGAnimatedPreserveAspectRatio: false,
  1500. SVGAnimatedRect : false,
  1501. SVGAnimatedString : false,
  1502. SVGAnimatedTransformList: false,
  1503. SVGAnimationElement : false,
  1504. SVGCSSRule : false,
  1505. SVGCircleElement : false,
  1506. SVGClipPathElement : false,
  1507. SVGColor : false,
  1508. SVGColorProfileElement: false,
  1509. SVGColorProfileRule : false,
  1510. SVGComponentTransferFunctionElement: false,
  1511. SVGCursorElement : false,
  1512. SVGDefsElement : false,
  1513. SVGDescElement : false,
  1514. SVGDocument : false,
  1515. SVGElement : false,
  1516. SVGElementInstance : false,
  1517. SVGElementInstanceList: false,
  1518. SVGEllipseElement : false,
  1519. SVGExternalResourcesRequired: false,
  1520. SVGFEBlendElement : false,
  1521. SVGFEColorMatrixElement: false,
  1522. SVGFEComponentTransferElement: false,
  1523. SVGFECompositeElement: false,
  1524. SVGFEConvolveMatrixElement: false,
  1525. SVGFEDiffuseLightingElement: false,
  1526. SVGFEDisplacementMapElement: false,
  1527. SVGFEDistantLightElement: false,
  1528. SVGFEFloodElement : false,
  1529. SVGFEFuncAElement : false,
  1530. SVGFEFuncBElement : false,
  1531. SVGFEFuncGElement : false,
  1532. SVGFEFuncRElement : false,
  1533. SVGFEGaussianBlurElement: false,
  1534. SVGFEImageElement : false,
  1535. SVGFEMergeElement : false,
  1536. SVGFEMergeNodeElement: false,
  1537. SVGFEMorphologyElement: false,
  1538. SVGFEOffsetElement : false,
  1539. SVGFEPointLightElement: false,
  1540. SVGFESpecularLightingElement: false,
  1541. SVGFESpotLightElement: false,
  1542. SVGFETileElement : false,
  1543. SVGFETurbulenceElement: false,
  1544. SVGFilterElement : false,
  1545. SVGFilterPrimitiveStandardAttributes: false,
  1546. SVGFitToViewBox : false,
  1547. SVGFontElement : false,
  1548. SVGFontFaceElement : false,
  1549. SVGFontFaceFormatElement: false,
  1550. SVGFontFaceNameElement: false,
  1551. SVGFontFaceSrcElement: false,
  1552. SVGFontFaceUriElement: false,
  1553. SVGForeignObjectElement: false,
  1554. SVGGElement : false,
  1555. SVGGlyphElement : false,
  1556. SVGGlyphRefElement : false,
  1557. SVGGradientElement : false,
  1558. SVGHKernElement : false,
  1559. SVGICCColor : false,
  1560. SVGImageElement : false,
  1561. SVGLangSpace : false,
  1562. SVGLength : false,
  1563. SVGLengthList : false,
  1564. SVGLineElement : false,
  1565. SVGLinearGradientElement: false,
  1566. SVGLocatable : false,
  1567. SVGMPathElement : false,
  1568. SVGMarkerElement : false,
  1569. SVGMaskElement : false,
  1570. SVGMatrix : false,
  1571. SVGMetadataElement : false,
  1572. SVGMissingGlyphElement: false,
  1573. SVGNumber : false,
  1574. SVGNumberList : false,
  1575. SVGPaint : false,
  1576. SVGPathElement : false,
  1577. SVGPathSeg : false,
  1578. SVGPathSegArcAbs : false,
  1579. SVGPathSegArcRel : false,
  1580. SVGPathSegClosePath : false,
  1581. SVGPathSegCurvetoCubicAbs: false,
  1582. SVGPathSegCurvetoCubicRel: false,
  1583. SVGPathSegCurvetoCubicSmoothAbs: false,
  1584. SVGPathSegCurvetoCubicSmoothRel: false,
  1585. SVGPathSegCurvetoQuadraticAbs: false,
  1586. SVGPathSegCurvetoQuadraticRel: false,
  1587. SVGPathSegCurvetoQuadraticSmoothAbs: false,
  1588. SVGPathSegCurvetoQuadraticSmoothRel: false,
  1589. SVGPathSegLinetoAbs : false,
  1590. SVGPathSegLinetoHorizontalAbs: false,
  1591. SVGPathSegLinetoHorizontalRel: false,
  1592. SVGPathSegLinetoRel : false,
  1593. SVGPathSegLinetoVerticalAbs: false,
  1594. SVGPathSegLinetoVerticalRel: false,
  1595. SVGPathSegList : false,
  1596. SVGPathSegMovetoAbs : false,
  1597. SVGPathSegMovetoRel : false,
  1598. SVGPatternElement : false,
  1599. SVGPoint : false,
  1600. SVGPointList : false,
  1601. SVGPolygonElement : false,
  1602. SVGPolylineElement : false,
  1603. SVGPreserveAspectRatio: false,
  1604. SVGRadialGradientElement: false,
  1605. SVGRect : false,
  1606. SVGRectElement : false,
  1607. SVGRenderingIntent : false,
  1608. SVGSVGElement : false,
  1609. SVGScriptElement : false,
  1610. SVGSetElement : false,
  1611. SVGStopElement : false,
  1612. SVGStringList : false,
  1613. SVGStylable : false,
  1614. SVGStyleElement : false,
  1615. SVGSwitchElement : false,
  1616. SVGSymbolElement : false,
  1617. SVGTRefElement : false,
  1618. SVGTSpanElement : false,
  1619. SVGTests : false,
  1620. SVGTextContentElement: false,
  1621. SVGTextElement : false,
  1622. SVGTextPathElement : false,
  1623. SVGTextPositioningElement: false,
  1624. SVGTitleElement : false,
  1625. SVGTransform : false,
  1626. SVGTransformList : false,
  1627. SVGTransformable : false,
  1628. SVGURIReference : false,
  1629. SVGUnitTypes : false,
  1630. SVGUseElement : false,
  1631. SVGVKernElement : false,
  1632. SVGViewElement : false,
  1633. SVGViewSpec : false,
  1634. SVGZoomAndPan : false,
  1635. TimeEvent : false,
  1636. top : false,
  1637. Uint16Array : false,
  1638. Uint32Array : false,
  1639. Uint8Array : false,
  1640. Uint8ClampedArray : false,
  1641. WebSocket : false,
  1642. window : false,
  1643. Worker : false,
  1644. XMLHttpRequest : false,
  1645. XMLSerializer : false,
  1646. XPathEvaluator : false,
  1647. XPathException : false,
  1648. XPathExpression : false,
  1649. XPathNamespace : false,
  1650. XPathNSResolver : false,
  1651. XPathResult : false
  1652. };
  1653. exports.devel = {
  1654. alert : false,
  1655. confirm: false,
  1656. console: false,
  1657. Debug : false,
  1658. opera : false,
  1659. prompt : false
  1660. };
  1661. exports.worker = {
  1662. importScripts: true,
  1663. postMessage : true,
  1664. self : true
  1665. };
  1666. // Widely adopted global names that are not part of ECMAScript standard
  1667. exports.nonstandard = {
  1668. escape : false,
  1669. unescape: false
  1670. };
  1671. // Globals provided by popular JavaScript environments.
  1672. exports.couch = {
  1673. "require" : false,
  1674. respond : false,
  1675. getRow : false,
  1676. emit : false,
  1677. send : false,
  1678. start : false,
  1679. sum : false,
  1680. log : false,
  1681. exports : false,
  1682. module : false,
  1683. provides : false
  1684. };
  1685. exports.node = {
  1686. __filename : false,
  1687. __dirname : false,
  1688. Buffer : false,
  1689. DataView : false,
  1690. console : false,
  1691. exports : true, // In Node it is ok to exports = module.exports = foo();
  1692. GLOBAL : false,
  1693. global : false,
  1694. module : false,
  1695. process : false,
  1696. require : false,
  1697. setTimeout : false,
  1698. clearTimeout : false,
  1699. setInterval : false,
  1700. clearInterval : false,
  1701. setImmediate : false, // v0.9.1+
  1702. clearImmediate: false // v0.9.1+
  1703. };
  1704. exports.phantom = {
  1705. phantom : true,
  1706. require : true,
  1707. WebPage : true
  1708. };
  1709. exports.rhino = {
  1710. defineClass : false,
  1711. deserialize : false,
  1712. gc : false,
  1713. help : false,
  1714. importPackage: false,
  1715. "java" : false,
  1716. load : false,
  1717. loadClass : false,
  1718. print : false,
  1719. quit : false,
  1720. readFile : false,
  1721. readUrl : false,
  1722. runCommand : false,
  1723. seal : false,
  1724. serialize : false,
  1725. spawn : false,
  1726. sync : false,
  1727. toint32 : false,
  1728. version : false
  1729. };
  1730. exports.shelljs = {
  1731. target : false,
  1732. echo : false,
  1733. exit : false,
  1734. cd : false,
  1735. pwd : false,
  1736. ls : false,
  1737. find : false,
  1738. cp : false,
  1739. rm : false,
  1740. mv : false,
  1741. mkdir : false,
  1742. test : false,
  1743. cat : false,
  1744. sed : false,
  1745. grep : false,
  1746. which : false,
  1747. dirs : false,
  1748. pushd : false,
  1749. popd : false,
  1750. env : false,
  1751. exec : false,
  1752. chmod : false,
  1753. config : false,
  1754. error : false,
  1755. tempdir : false
  1756. };
  1757. exports.wsh = {
  1758. ActiveXObject : true,
  1759. Enumerator : true,
  1760. GetObject : true,
  1761. ScriptEngine : true,
  1762. ScriptEngineBuildVersion : true,
  1763. ScriptEngineMajorVersion : true,
  1764. ScriptEngineMinorVersion : true,
  1765. VBArray : true,
  1766. WSH : true,
  1767. WScript : true,
  1768. XDomainRequest : true
  1769. };
  1770. // Globals provided by popular JavaScript libraries.
  1771. exports.dojo = {
  1772. dojo : false,
  1773. dijit : false,
  1774. dojox : false,
  1775. define : false,
  1776. "require": false
  1777. };
  1778. exports.jquery = {
  1779. "$" : false,
  1780. jQuery : false
  1781. };
  1782. exports.mootools = {
  1783. "$" : false,
  1784. "$$" : false,
  1785. Asset : false,
  1786. Browser : false,
  1787. Chain : false,
  1788. Class : false,
  1789. Color : false,
  1790. Cookie : false,
  1791. Core : false,
  1792. Document : false,
  1793. DomReady : false,
  1794. DOMEvent : false,
  1795. DOMReady : false,
  1796. Drag : false,
  1797. Element : false,
  1798. Elements : false,
  1799. Event : false,
  1800. Events : false,
  1801. Fx : false,
  1802. Group : false,
  1803. Hash : false,
  1804. HtmlTable : false,
  1805. Iframe : false,
  1806. IframeShim : false,
  1807. InputValidator: false,
  1808. instanceOf : false,
  1809. Keyboard : false,
  1810. Locale : false,
  1811. Mask : false,
  1812. MooTools : false,
  1813. Native : false,
  1814. Options : false,
  1815. OverText : false,
  1816. Request : false,
  1817. Scroller : false,
  1818. Slick : false,
  1819. Slider : false,
  1820. Sortables : false,
  1821. Spinner : false,
  1822. Swiff : false,
  1823. Tips : false,
  1824. Type : false,
  1825. typeOf : false,
  1826. URI : false,
  1827. Window : false
  1828. };
  1829. exports.prototypejs = {
  1830. "$" : false,
  1831. "$$" : false,
  1832. "$A" : false,
  1833. "$F" : false,
  1834. "$H" : false,
  1835. "$R" : false,
  1836. "$break" : false,
  1837. "$continue" : false,
  1838. "$w" : false,
  1839. Abstract : false,
  1840. Ajax : false,
  1841. Class : false,
  1842. Enumerable : false,
  1843. Element : false,
  1844. Event : false,
  1845. Field : false,
  1846. Form : false,
  1847. Hash : false,
  1848. Insertion : false,
  1849. ObjectRange : false,
  1850. PeriodicalExecuter: false,
  1851. Position : false,
  1852. Prototype : false,
  1853. Selector : false,
  1854. Template : false,
  1855. Toggle : false,
  1856. Try : false,
  1857. Autocompleter : false,
  1858. Builder : false,
  1859. Control : false,
  1860. Draggable : false,
  1861. Draggables : false,
  1862. Droppables : false,
  1863. Effect : false,
  1864. Sortable : false,
  1865. SortableObserver : false,
  1866. Sound : false,
  1867. Scriptaculous : false
  1868. };
  1869. exports.yui = {
  1870. YUI : false,
  1871. Y : false,
  1872. YUI_config: false
  1873. };
  1874. },
  1875. {}],
  1876. "n4bKNg":[function(req,module,exports){
  1877. /*!
  1878. * JSHint, by JSHint Community.
  1879. *
  1880. * This file (and this file only) is licensed under the same slightly modified
  1881. * MIT license that JSLint is. It stops evil-doers everywhere:
  1882. *
  1883. * Copyright (c) 2002 Douglas Crockford (www.JSLint.com)
  1884. *
  1885. * Permission is hereby granted, free of charge, to any person obtaining
  1886. * a copy of this software and associated documentation files (the "Software"),
  1887. * to deal in the Software without restriction, including without limitation
  1888. * the rights to use, copy, modify, merge, publish, distribute, sublicense,
  1889. * and/or sell copies of the Software, and to permit persons to whom
  1890. * the Software is furnished to do so, subject to the following conditions:
  1891. *
  1892. * The above copyright notice and this permission notice shall be included
  1893. * in all copies or substantial portions of the Software.
  1894. *
  1895. * The Software shall be used for Good, not Evil.
  1896. *
  1897. * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  1898. * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  1899. * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  1900. * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  1901. * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
  1902. * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
  1903. * DEALINGS IN THE SOFTWARE.
  1904. *
  1905. */
  1906. /*jshint quotmark:double */
  1907. /*global console:true */
  1908. /*exported console */
  1909. var _ = req("underscore");
  1910. var events = req("events");
  1911. var vars = req("../shared/vars.js");
  1912. var messages = req("../shared/messages.js");
  1913. var Lexer = req("./lex.js").Lexer;
  1914. var reg = req("./reg.js");
  1915. var state = req("./state.js").state;
  1916. var style = req("./style.js");
  1917. // We need this module here because environments such as IE and Rhino
  1918. // don't necessarilly expose the 'console' API and browserify uses
  1919. // it to log things. It's a sad state of affair, really.
  1920. var console = req("console-browserify");
  1921. // We build the application inside a function so that we produce only a singleton
  1922. // variable. That function will be invoked immediately, and its return value is
  1923. // the JSHINT function itself.
  1924. var JSHINT = (function () {
  1925. "use strict";
  1926. var anonname, // The guessed name for anonymous functions.
  1927. api, // Extension API
  1928. // These are operators that should not be used with the ! operator.
  1929. bang = {
  1930. "<" : true,
  1931. "<=" : true,
  1932. "==" : true,
  1933. "===": true,
  1934. "!==": true,
  1935. "!=" : true,
  1936. ">" : true,
  1937. ">=" : true,
  1938. "+" : true,
  1939. "-" : true,
  1940. "*" : true,
  1941. "/" : true,
  1942. "%" : true
  1943. },
  1944. // These are the JSHint boolean options.
  1945. boolOptions = {
  1946. asi : true, // if automatic semicolon insertion should be tolerated
  1947. bitwise : true, // if bitwise operators should not be allowed
  1948. boss : true, // if advanced usage of assignments should be allowed
  1949. browser : true, // if the standard browser globals should be predefined
  1950. camelcase : true, // if identifiers should be required in camel case
  1951. couch : true, // if CouchDB globals should be predefined
  1952. curly : true, // if curly braces around all blocks should be required
  1953. debug : true, // if debugger statements should be allowed
  1954. devel : true, // if logging globals should be predefined (console, alert, etc.)
  1955. dojo : true, // if Dojo Toolkit globals should be predefined
  1956. eqeqeq : true, // if === should be required
  1957. eqnull : true, // if == null comparisons should be tolerated
  1958. es3 : true, // if ES3 syntax should be allowed
  1959. es5 : true, // if ES5 syntax should be allowed (is now set per default)
  1960. esnext : true, // if es.next specific syntax should be allowed
  1961. moz : true, // if mozilla specific syntax should be allowed
  1962. evil : true, // if eval should be allowed
  1963. expr : true, // if ExpressionStatement should be allowed as Programs
  1964. forin : true, // if for in statements must filter
  1965. funcscope : true, // if only function scope should be used for scope tests
  1966. gcl : true, // if JSHint should be compatible with Google Closure Linter
  1967. globalstrict: true, // if global "use strict"; should be allowed (also enables 'strict')
  1968. immed : true, // if immediate invocations must be wrapped in parens
  1969. iterator : true, // if the `__iterator__` property should be allowed
  1970. jquery : true, // if jQuery globals should be predefined
  1971. lastsemic : true, // if semicolons may be ommitted for the trailing
  1972. // statements inside of a one-line blocks.
  1973. laxbreak : true, // if line breaks should not be checked
  1974. laxcomma : true, // if line breaks should not be checked around commas
  1975. loopfunc : true, // if functions should be allowed to be defined within
  1976. // loops
  1977. mootools : true, // if MooTools globals should be predefined
  1978. multistr : true, // allow multiline strings
  1979. newcap : true, // if constructor names must be capitalized
  1980. noarg : true, // if arguments.caller and arguments.callee should be
  1981. // disallowed
  1982. node : true, // if the Node.js environment globals should be
  1983. // predefined
  1984. noempty : true, // if empty blocks should be disallowed
  1985. nonew : true, // if using `new` for side-effects should be disallowed
  1986. nonstandard : true, // if non-standard (but widely adopted) globals should
  1987. // be predefined
  1988. nomen : true, // if names should be checked
  1989. onevar : true, // if only one var statement per function should be
  1990. // allowed
  1991. passfail : true, // if the scan should stop on first error
  1992. phantom : true, // if PhantomJS symbols should be allowed
  1993. plusplus : true, // if increment/decrement should not be allowed
  1994. proto : true, // if the `__proto__` property should be allowed
  1995. prototypejs : true, // if Prototype and Scriptaculous globals should be
  1996. // predefined
  1997. rhino : true, // if the Rhino environment globals should be predefined
  1998. shelljs : true, // if ShellJS globals should be predefined
  1999. undef : true, // if variables should be declared before used
  2000. scripturl : true, // if script-targeted URLs should be tolerated
  2001. shadow : true, // if variable shadowing should be tolerated
  2002. smarttabs : true, // if smarttabs should be tolerated
  2003. // (http://www.emacswiki.org/emacs/SmartTabs)
  2004. strict : true, // require the "use strict"; pragma
  2005. sub : true, // if all forms of subscript notation are tolerated
  2006. supernew : true, // if `new function () { ... };` and `new Object;`
  2007. // should be tolerated
  2008. trailing : true, // if trailing whitespace rules apply
  2009. validthis : true, // if 'this' inside a non-constructor function is valid.
  2010. // This is a function scoped option only.
  2011. withstmt : true, // if with statements should be allowed
  2012. white : true, // if strict whitespace rules apply
  2013. worker : true, // if Web Worker script symbols should be allowed
  2014. wsh : true, // if the Windows Scripting Host environment globals
  2015. // should be predefined
  2016. yui : true, // YUI variables should be predefined
  2017. // Obsolete options
  2018. onecase : true, // if one case switch statements should be allowed
  2019. regexp : true, // if the . should not be allowed in regexp literals
  2020. regexdash : true // if unescaped first/last dash (-) inside brackets
  2021. // should be tolerated
  2022. },
  2023. // These are the JSHint options that can take any value
  2024. // (we use this object to detect invalid options)
  2025. valOptions = {
  2026. maxlen : false,
  2027. indent : false,
  2028. maxerr : false,
  2029. predef : false,
  2030. quotmark : false, //'single'|'double'|true
  2031. scope : false,
  2032. maxstatements: false, // {int} max statements per function
  2033. maxdepth : false, // {int} max nested block depth per function
  2034. maxparams : false, // {int} max params per function
  2035. maxcomplexity: false, // {int} max cyclomatic complexity per function
  2036. unused : true, // warn if variables are unused. Available options:
  2037. // false - don't check for unused variables
  2038. // true - "vars" + check last function param
  2039. // "vars" - skip checking unused function params
  2040. // "strict" - "vars" + check all function params
  2041. latedef : false // warn if the variable is used before its definition
  2042. // false - don't emit any warnings
  2043. // true - warn if any variable is used before its definition
  2044. // "nofunc" - warn for any variable but function declarations
  2045. },
  2046. // These are JSHint boolean options which are shared with JSLint
  2047. // where the definition in JSHint is opposite JSLint
  2048. invertedOptions = {
  2049. bitwise : true,
  2050. forin : true,
  2051. newcap : true,
  2052. nomen : true,
  2053. plusplus: true,
  2054. regexp : true,
  2055. undef : true,
  2056. white : true,
  2057. // Inverted and renamed, use JSHint name here
  2058. eqeqeq : true,
  2059. onevar : true,
  2060. strict : true
  2061. },
  2062. // These are JSHint boolean options which are shared with JSLint
  2063. // where the name has been changed but the effect is unchanged
  2064. renamedOptions = {
  2065. eqeq : "eqeqeq",
  2066. vars : "onevar",
  2067. windows: "wsh",
  2068. sloppy : "strict"
  2069. },
  2070. declared, // Globals that were declared using /*global ... */ syntax.
  2071. exported, // Variables that are used outside of the current file.
  2072. functionicity = [
  2073. "closure", "exception", "global", "label",
  2074. "outer", "unused", "var"
  2075. ],
  2076. funct, // The current function
  2077. functions, // All of the functions
  2078. global, // The global scope
  2079. implied, // Implied globals
  2080. inblock,
  2081. indent,
  2082. lookahead,
  2083. lex,
  2084. member,
  2085. membersOnly,
  2086. noreach,
  2087. predefined, // Global variables defined by option
  2088. scope, // The current scope
  2089. stack,
  2090. unuseds,
  2091. urls,
  2092. warnings,
  2093. extraModules = [],
  2094. emitter = new events.EventEmitter();
  2095. function checkOption(name, t) {
  2096. name = name.trim();
  2097. if (/^[+-]W\d{3}$/g.test(name)) {
  2098. return true;
  2099. }
  2100. if (valOptions[name] === undefined && boolOptions[name] === undefined) {
  2101. if (t.type !== "jslint") {
  2102. error("E001", t, name);
  2103. return false;
  2104. }
  2105. }
  2106. return true;
  2107. }
  2108. function isString(obj) {
  2109. return Object.prototype.toString.call(obj) === "[object String]";
  2110. }
  2111. function isIdentifier(tkn, value) {
  2112. if (!tkn)
  2113. return false;
  2114. if (!tkn.identifier || tkn.value !== value)
  2115. return false;
  2116. return true;
  2117. }
  2118. function isReserved(token) {
  2119. if (!token.reserved) {
  2120. return false;
  2121. }
  2122. var meta = token.meta;
  2123. if (meta && meta.isFutureReservedWord && state.option.inES5()) {
  2124. // ES3 FutureReservedWord in an ES5 environment.
  2125. if (!meta.es5) {
  2126. return false;
  2127. }
  2128. // Some ES5 FutureReservedWord identifiers are active only
  2129. // within a strict mode environment.
  2130. if (meta.strictOnly) {
  2131. if (!state.option.strict && !state.directive["use strict"]) {
  2132. return false;
  2133. }
  2134. }
  2135. if (token.isProperty) {
  2136. return false;
  2137. }
  2138. }
  2139. return true;
  2140. }
  2141. function supplant(str, data) {
  2142. return str.replace(/\{([^{}]*)\}/g, function (a, b) {
  2143. var r = data[b];
  2144. return typeof r === "string" || typeof r === "number" ? r : a;
  2145. });
  2146. }
  2147. function combine(t, o) {
  2148. var n;
  2149. for (n in o) {
  2150. if (_.has(o, n) && !_.has(JSHINT.blacklist, n)) {
  2151. t[n] = o[n];
  2152. }
  2153. }
  2154. }
  2155. function updatePredefined() {
  2156. Object.keys(JSHINT.blacklist).forEach(function (key) {
  2157. delete predefined[key];
  2158. });
  2159. }
  2160. function assume() {
  2161. if (state.option.couch) {
  2162. combine(predefined, vars.couch);
  2163. }
  2164. if (state.option.rhino) {
  2165. combine(predefined, vars.rhino);
  2166. }
  2167. if (state.option.shelljs) {
  2168. combine(predefined, vars.shelljs);
  2169. combine(predefined, vars.node);
  2170. }
  2171. if (state.option.phantom) {
  2172. combine(predefined, vars.phantom);
  2173. }
  2174. if (state.option.prototypejs) {
  2175. combine(predefined, vars.prototypejs);
  2176. }
  2177. if (state.option.node) {
  2178. combine(predefined, vars.node);
  2179. }
  2180. if (state.option.devel) {
  2181. combine(predefined, vars.devel);
  2182. }
  2183. if (state.option.dojo) {
  2184. combine(predefined, vars.dojo);
  2185. }
  2186. if (state.option.browser) {
  2187. combine(predefined, vars.browser);
  2188. }
  2189. if (state.option.nonstandard) {
  2190. combine(predefined, vars.nonstandard);
  2191. }
  2192. if (state.option.jquery) {
  2193. combine(predefined, vars.jquery);
  2194. }
  2195. if (state.option.mootools) {
  2196. combine(predefined, vars.mootools);
  2197. }
  2198. if (state.option.worker) {
  2199. combine(predefined, vars.worker);
  2200. }
  2201. if (state.option.wsh) {
  2202. combine(predefined, vars.wsh);
  2203. }
  2204. if (state.option.globalstrict && state.option.strict !== false) {
  2205. state.option.strict = true;
  2206. }
  2207. if (state.option.yui) {
  2208. combine(predefined, vars.yui);
  2209. }
  2210. // Let's assume that chronologically ES3 < ES5 < ES6/ESNext < Moz
  2211. state.option.inMoz = function (strict) {
  2212. return state.option.moz;
  2213. };
  2214. state.option.inESNext = function (strict) {
  2215. return state.option.moz || state.option.esnext;
  2216. };
  2217. state.option.inES5 = function (/* strict */) {
  2218. return !state.option.es3;
  2219. };
  2220. state.option.inES3 = function (strict) {
  2221. if (strict) {
  2222. return !state.option.moz && !state.option.esnext && state.option.es3;
  2223. }
  2224. return state.option.es3;
  2225. };
  2226. }
  2227. // Produce an error warning.
  2228. function quit(code, line, chr) {
  2229. var percentage = Math.floor((line / state.lines.length) * 100);
  2230. var message = messages.errors[code].desc;
  2231. throw {
  2232. name: "JSHintError",
  2233. line: line,
  2234. character: chr,
  2235. message: message + " (" + percentage + "% scanned).",
  2236. raw: message,
  2237. code: code
  2238. };
  2239. }
  2240. function isundef(scope, code, token, a) {
  2241. return JSHINT.undefs.push([scope, code, token, a]);
  2242. }
  2243. function warning(code, t, a, b, c, d) {
  2244. var ch, l, w, msg;
  2245. if (/^W\d{3}$/.test(code)) {
  2246. if (state.ignored[code])
  2247. return;
  2248. msg = messages.warnings[code];
  2249. } else if (/E\d{3}/.test(code)) {
  2250. msg = messages.errors[code];
  2251. } else if (/I\d{3}/.test(code)) {
  2252. msg = messages.info[code];
  2253. }
  2254. t = t || state.tokens.next;
  2255. if (t.id === "(end)") { // `~
  2256. t = state.tokens.curr;
  2257. }
  2258. l = t.line || 0;
  2259. ch = t.from || 0;
  2260. w = {
  2261. id: "(error)",
  2262. raw: msg.desc,
  2263. code: msg.code,
  2264. evidence: state.lines[l - 1] || "",
  2265. line: l,
  2266. character: ch,
  2267. scope: JSHINT.scope,
  2268. a: a,
  2269. b: b,
  2270. c: c,
  2271. d: d
  2272. };
  2273. w.reason = supplant(msg.desc, w);
  2274. JSHINT.errors.push(w);
  2275. if (state.option.passfail) {
  2276. quit("E042", l, ch);
  2277. }
  2278. warnings += 1;
  2279. if (warnings >= state.option.maxerr) {
  2280. quit("E043", l, ch);
  2281. }
  2282. return w;
  2283. }
  2284. function warningAt(m, l, ch, a, b, c, d) {
  2285. return warning(m, {
  2286. line: l,
  2287. from: ch
  2288. }, a, b, c, d);
  2289. }
  2290. function error(m, t, a, b, c, d) {
  2291. warning(m, t, a, b, c, d);
  2292. }
  2293. function errorAt(m, l, ch, a, b, c, d) {
  2294. return error(m, {
  2295. line: l,
  2296. from: ch
  2297. }, a, b, c, d);
  2298. }
  2299. // Tracking of "internal" scripts, like eval containing a static string
  2300. function addInternalSrc(elem, src) {
  2301. var i;
  2302. i = {
  2303. id: "(internal)",
  2304. elem: elem,
  2305. value: src
  2306. };
  2307. JSHINT.internals.push(i);
  2308. return i;
  2309. }
  2310. function addlabel(t, type, tkn, islet) {
  2311. // Define t in the current function in the current scope.
  2312. if (type === "exception") {
  2313. if (_.has(funct["(context)"], t)) {
  2314. if (funct[t] !== true && !state.option.node) {
  2315. warning("W002", state.tokens.next, t);
  2316. }
  2317. }
  2318. }
  2319. if (_.has(funct, t) && !funct["(global)"]) {
  2320. if (funct[t] === true) {
  2321. if (state.option.latedef) {
  2322. if ((state.option.latedef === true && _.contains([funct[t], type], "unction")) ||
  2323. !_.contains([funct[t], type], "unction")) {
  2324. warning("W003", state.tokens.next, t);
  2325. }
  2326. }
  2327. } else {
  2328. if (!state.option.shadow && type !== "exception" ||
  2329. (funct["(blockscope)"].getlabel(t))) {
  2330. warning("W004", state.tokens.next, t);
  2331. }
  2332. }
  2333. }
  2334. // a double definition of a let variable in same block throws a TypeError
  2335. if (funct["(blockscope)"] && funct["(blockscope)"].current.has(t)) {
  2336. error("E044", state.tokens.next, t);
  2337. }
  2338. // if the identifier is from a let, adds it only to the current blockscope
  2339. if (islet) {
  2340. funct["(blockscope)"].current.add(t, type, state.tokens.curr);
  2341. } else {
  2342. funct[t] = type;
  2343. if (tkn) {
  2344. funct["(tokens)"][t] = tkn;
  2345. }
  2346. if (funct["(global)"]) {
  2347. global[t] = funct;
  2348. if (_.has(implied, t)) {
  2349. if (state.option.latedef) {
  2350. if ((state.option.latedef === true && _.contains([funct[t], type], "unction")) ||
  2351. !_.contains([funct[t], type], "unction")) {
  2352. warning("W003", state.tokens.next, t);
  2353. }
  2354. }
  2355. delete implied[t];
  2356. }
  2357. } else {
  2358. scope[t] = funct;
  2359. }
  2360. }
  2361. }
  2362. function doOption() {
  2363. var nt = state.tokens.next;
  2364. var body = nt.body.match(/(-\s+)?[^\s,]+(?:\s*:\s*(-\s+)?[^\s,]+)?/g);
  2365. var predef = {};
  2366. if (nt.type === "globals") {
  2367. body.forEach(function (g) {
  2368. g = g.split(":");
  2369. var key = (g[0] || "").trim();
  2370. var val = (g[1] || "").trim();
  2371. if (key.charAt(0) === "-") {
  2372. key = key.slice(1);
  2373. val = false;
  2374. JSHINT.blacklist[key] = key;
  2375. updatePredefined();
  2376. } else {
  2377. predef[key] = (val === "true");
  2378. }
  2379. });
  2380. combine(predefined, predef);
  2381. for (var key in predef) {
  2382. if (_.has(predef, key)) {
  2383. declared[key] = nt;
  2384. }
  2385. }
  2386. }
  2387. if (nt.type === "exported") {
  2388. body.forEach(function (e) {
  2389. exported[e] = true;
  2390. });
  2391. }
  2392. if (nt.type === "members") {
  2393. membersOnly = membersOnly || {};
  2394. body.forEach(function (m) {
  2395. var ch1 = m.charAt(0);
  2396. var ch2 = m.charAt(m.length - 1);
  2397. if (ch1 === ch2 && (ch1 === "\"" || ch1 === "'")) {
  2398. m = m
  2399. .substr(1, m.length - 2)
  2400. .replace("\\b", "\b")
  2401. .replace("\\t", "\t")
  2402. .replace("\\n", "\n")
  2403. .replace("\\v", "\v")
  2404. .replace("\\f", "\f")
  2405. .replace("\\r", "\r")
  2406. .replace("\\\\", "\\")
  2407. .replace("\\\"", "\"");
  2408. }
  2409. membersOnly[m] = false;
  2410. });
  2411. }
  2412. var numvals = [
  2413. "maxstatements",
  2414. "maxparams",
  2415. "maxdepth",
  2416. "maxcomplexity",
  2417. "maxerr",
  2418. "maxlen",
  2419. "indent"
  2420. ];
  2421. if (nt.type === "jshint" || nt.type === "jslint") {
  2422. body.forEach(function (g) {
  2423. g = g.split(":");
  2424. var key = (g[0] || "").trim();
  2425. var val = (g[1] || "").trim();
  2426. if (!checkOption(key, nt)) {
  2427. return;
  2428. }
  2429. if (numvals.indexOf(key) >= 0) {
  2430. // GH988 - numeric options can be disabled by setting them to `false`
  2431. if (val !== "false") {
  2432. val = +val;
  2433. if (typeof val !== "number" || !isFinite(val) || val <= 0 || Math.floor(val) !== val) {
  2434. error("E032", nt, g[1].trim());
  2435. return;
  2436. }
  2437. if (key === "indent") {
  2438. state.option["(explicitIndent)"] = true;
  2439. }
  2440. state.option[key] = val;
  2441. } else {
  2442. if (key === "indent") {
  2443. state.option["(explicitIndent)"] = false;
  2444. } else {
  2445. state.option[key] = false;
  2446. }
  2447. }
  2448. return;
  2449. }
  2450. if (key === "validthis") {
  2451. // `validthis` is valid only within a function scope.
  2452. if (funct["(global)"]) {
  2453. error("E009");
  2454. } else {
  2455. if (val === "true" || val === "false") {
  2456. state.option.validthis = (val === "true");
  2457. } else {
  2458. error("E002", nt);
  2459. }
  2460. }
  2461. return;
  2462. }
  2463. if (key === "quotmark") {
  2464. switch (val) {
  2465. case "true":
  2466. case "false":
  2467. state.option.quotmark = (val === "true");
  2468. break;
  2469. case "double":
  2470. case "single":
  2471. state.option.quotmark = val;
  2472. break;
  2473. default:
  2474. error("E002", nt);
  2475. }
  2476. return;
  2477. }
  2478. if (key === "unused") {
  2479. switch (val) {
  2480. case "true":
  2481. state.option.unused = true;
  2482. break;
  2483. case "false":
  2484. state.option.unused = false;
  2485. break;
  2486. case "vars":
  2487. case "strict":
  2488. state.option.unused = val;
  2489. break;
  2490. default:
  2491. error("E002", nt);
  2492. }
  2493. return;
  2494. }
  2495. if (key === "latedef") {
  2496. switch (val) {
  2497. case "true":
  2498. state.option.latedef = true;
  2499. break;
  2500. case "false":
  2501. state.option.latedef = false;
  2502. break;
  2503. case "nofunc":
  2504. state.option.latedef = "nofunc";
  2505. break;
  2506. default:
  2507. error("E002", nt);
  2508. }
  2509. return;
  2510. }
  2511. var match = /^([+-])(W\d{3})$/g.exec(key);
  2512. if (match) {
  2513. // ignore for -W..., unignore for +W...
  2514. state.ignored[match[2]] = (match[1] === "-");
  2515. return;
  2516. }
  2517. var tn;
  2518. if (val === "true" || val === "false") {
  2519. if (nt.type === "jslint") {
  2520. tn = renamedOptions[key] || key;
  2521. state.option[tn] = (val === "true");
  2522. if (invertedOptions[tn] !== undefined) {
  2523. state.option[tn] = !state.option[tn];
  2524. }
  2525. } else {
  2526. state.option[key] = (val === "true");
  2527. }
  2528. if (key === "newcap") {
  2529. state.option["(explicitNewcap)"] = true;
  2530. }
  2531. return;
  2532. }
  2533. error("E002", nt);
  2534. });
  2535. assume();
  2536. }
  2537. }
  2538. // We need a peek function. If it has an argument, it peeks that much farther
  2539. // ahead. It is used to distinguish
  2540. // for ( var i in ...
  2541. // from
  2542. // for ( var i = ...
  2543. function peek(p) {
  2544. var i = p || 0, j = 0, t;
  2545. while (j <= i) {
  2546. t = lookahead[j];
  2547. if (!t) {
  2548. t = lookahead[j] = lex.token();
  2549. }
  2550. j += 1;
  2551. }
  2552. return t;
  2553. }
  2554. // Produce the next token. It looks for programming errors.
  2555. function advance(id, t) {
  2556. switch (state.tokens.curr.id) {
  2557. case "(number)":
  2558. if (state.tokens.next.id === ".") {
  2559. warning("W005", state.tokens.curr);
  2560. }
  2561. break;
  2562. case "-":
  2563. if (state.tokens.next.id === "-" || state.tokens.next.id === "--") {
  2564. warning("W006");
  2565. }
  2566. break;
  2567. case "+":
  2568. if (state.tokens.next.id === "+" || state.tokens.next.id === "++") {
  2569. warning("W007");
  2570. }
  2571. break;
  2572. }
  2573. if (state.tokens.curr.type === "(string)" || state.tokens.curr.identifier) {
  2574. anonname = state.tokens.curr.value;
  2575. }
  2576. if (id && state.tokens.next.id !== id) {
  2577. if (t) {
  2578. if (state.tokens.next.id === "(end)") {
  2579. error("E019", t, t.id);
  2580. } else {
  2581. error("E020", state.tokens.next, id, t.id, t.line, state.tokens.next.value);
  2582. }
  2583. } else if (state.tokens.next.type !== "(identifier)" || state.tokens.next.value !== id) {
  2584. warning("W116", state.tokens.next, id, state.tokens.next.value);
  2585. }
  2586. }
  2587. state.tokens.prev = state.tokens.curr;
  2588. state.tokens.curr = state.tokens.next;
  2589. for (;;) {
  2590. state.tokens.next = lookahead.shift() || lex.token();
  2591. if (!state.tokens.next) { // No more tokens left, give up
  2592. quit("E041", state.tokens.curr.line);
  2593. }
  2594. if (state.tokens.next.id === "(end)" || state.tokens.next.id === "(error)") {
  2595. return;
  2596. }
  2597. if (state.tokens.next.check) {
  2598. state.tokens.next.check();
  2599. }
  2600. if (state.tokens.next.isSpecial) {
  2601. doOption();
  2602. } else {
  2603. if (state.tokens.next.id !== "(endline)") {
  2604. break;
  2605. }
  2606. }
  2607. }
  2608. }
  2609. function isInfix(token) {
  2610. return token.infix || (!token.identifier && !!token.led);
  2611. }
  2612. function isEndOfExpr() {
  2613. var curr = state.tokens.curr;
  2614. var next = state.tokens.next;
  2615. if (next.id === ";" || next.id === "}" || next.id === ":") {
  2616. return true;
  2617. }
  2618. if (isInfix(next) === isInfix(curr) || (curr.id === "yield" && state.option.inMoz(true))) {
  2619. return curr.line !== next.line;
  2620. }
  2621. return false;
  2622. }
  2623. // This is the heart of JSHINT, the Pratt parser. In addition to parsing, it
  2624. // is looking for ad hoc lint patterns. We add .fud to Pratt's model, which is
  2625. // like .nud except that it is only used on the first token of a statement.
  2626. // Having .fud makes it much easier to define statement-oriented languages like
  2627. // JavaScript. I retained Pratt's nomenclature.
  2628. // .nud Null denotation
  2629. // .fud First null denotation
  2630. // .led Left denotation
  2631. // lbp Left binding power
  2632. // rbp Right binding power
  2633. // They are elements of the parsing method called Top Down Operator Precedence.
  2634. function expression(rbp, initial) {
  2635. var left, isArray = false, isObject = false, isLetExpr = false;
  2636. // if current expression is a let expression
  2637. if (!initial && state.tokens.next.value === "let" && peek(0).value === "(") {
  2638. if (!state.option.inMoz(true)) {
  2639. warning("W118", state.tokens.next, "let expressions");
  2640. }
  2641. isLetExpr = true;
  2642. // create a new block scope we use only for the current expression
  2643. funct["(blockscope)"].stack();
  2644. advance("let");
  2645. advance("(");
  2646. state.syntax["let"].fud.call(state.syntax["let"].fud, false);
  2647. advance(")");
  2648. }
  2649. if (state.tokens.next.id === "(end)")
  2650. error("E006", state.tokens.curr);
  2651. advance();
  2652. if (initial) {
  2653. anonname = "anonymous";
  2654. funct["(verb)"] = state.tokens.curr.value;
  2655. }
  2656. if (initial === true && state.tokens.curr.fud) {
  2657. left = state.tokens.curr.fud();
  2658. } else {
  2659. if (state.tokens.curr.nud) {
  2660. left = state.tokens.curr.nud();
  2661. } else {
  2662. error("E030", state.tokens.curr, state.tokens.curr.id);
  2663. }
  2664. while (rbp < state.tokens.next.lbp && !isEndOfExpr()) {
  2665. isArray = state.tokens.curr.value === "Array";
  2666. isObject = state.tokens.curr.value === "Object";
  2667. // #527, new Foo.Array(), Foo.Array(), new Foo.Object(), Foo.Object()
  2668. // Line breaks in IfStatement heads exist to satisfy the checkJSHint
  2669. // "Line too long." error.
  2670. if (left && (left.value || (left.first && left.first.value))) {
  2671. // If the left.value is not "new", or the left.first.value is a "."
  2672. // then safely assume that this is not "new Array()" and possibly
  2673. // not "new Object()"...
  2674. if (left.value !== "new" ||
  2675. (left.first && left.first.value && left.first.value === ".")) {
  2676. isArray = false;
  2677. // ...In the case of Object, if the left.value and state.tokens.curr.value
  2678. // are not equal, then safely assume that this not "new Object()"
  2679. if (left.value !== state.tokens.curr.value) {
  2680. isObject = false;
  2681. }
  2682. }
  2683. }
  2684. advance();
  2685. if (isArray && state.tokens.curr.id === "(" && state.tokens.next.id === ")") {
  2686. warning("W009", state.tokens.curr);
  2687. }
  2688. if (isObject && state.tokens.curr.id === "(" && state.tokens.next.id === ")") {
  2689. warning("W010", state.tokens.curr);
  2690. }
  2691. if (left && state.tokens.curr.led) {
  2692. left = state.tokens.curr.led(left);
  2693. } else {
  2694. error("E033", state.tokens.curr, state.tokens.curr.id);
  2695. }
  2696. }
  2697. }
  2698. if (isLetExpr) {
  2699. funct["(blockscope)"].unstack();
  2700. }
  2701. return left;
  2702. }
  2703. // Functions for conformance of style.
  2704. function adjacent(left, right) {
  2705. left = left || state.tokens.curr;
  2706. right = right || state.tokens.next;
  2707. if (state.option.white) {
  2708. if (left.character !== right.from && left.line === right.line) {
  2709. left.from += (left.character - left.from);
  2710. warning("W011", left, left.value);
  2711. }
  2712. }
  2713. }
  2714. function nobreak(left, right) {
  2715. left = left || state.tokens.curr;
  2716. right = right || state.tokens.next;
  2717. if (state.option.white && (left.character !== right.from || left.line !== right.line)) {
  2718. warning("W012", right, right.value);
  2719. }
  2720. }
  2721. function nospace(left, right) {
  2722. left = left || state.tokens.curr;
  2723. right = right || state.tokens.next;
  2724. if (state.option.white && !left.comment) {
  2725. if (left.line === right.line) {
  2726. adjacent(left, right);
  2727. }
  2728. }
  2729. }
  2730. function nonadjacent(left, right) {
  2731. if (state.option.white) {
  2732. left = left || state.tokens.curr;
  2733. right = right || state.tokens.next;
  2734. if (left.value === ";" && right.value === ";") {
  2735. return;
  2736. }
  2737. if (left.line === right.line && left.character === right.from) {
  2738. left.from += (left.character - left.from);
  2739. warning("W013", left, left.value);
  2740. }
  2741. }
  2742. }
  2743. function nobreaknonadjacent(left, right) {
  2744. left = left || state.tokens.curr;
  2745. right = right || state.tokens.next;
  2746. if (!state.option.laxbreak && left.line !== right.line) {
  2747. warning("W014", right, right.value);
  2748. } else if (state.option.white) {
  2749. left = left || state.tokens.curr;
  2750. right = right || state.tokens.next;
  2751. if (left.character === right.from) {
  2752. left.from += (left.character - left.from);
  2753. warning("W013", left, left.value);
  2754. }
  2755. }
  2756. }
  2757. function indentation(bias) {
  2758. if (!state.option.white && !state.option["(explicitIndent)"]) {
  2759. return;
  2760. }
  2761. if (state.tokens.next.id === "(end)") {
  2762. return;
  2763. }
  2764. var i = indent + (bias || 0);
  2765. if (state.tokens.next.from !== i) {
  2766. warning("W015", state.tokens.next, state.tokens.next.value, i, state.tokens.next.from);
  2767. }
  2768. }
  2769. function nolinebreak(t) {
  2770. t = t || state.tokens.curr;
  2771. if (t.line !== state.tokens.next.line) {
  2772. warning("E022", t, t.value);
  2773. }
  2774. }
  2775. function nobreakcomma(left, right) {
  2776. if (left.line !== right.line) {
  2777. if (!state.option.laxcomma) {
  2778. if (comma.first) {
  2779. warning("I001");
  2780. comma.first = false;
  2781. }
  2782. warning("W014", left, right.value);
  2783. }
  2784. } else if (!left.comment && left.character !== right.from && state.option.white) {
  2785. left.from += (left.character - left.from);
  2786. warning("W011", left, left.value);
  2787. }
  2788. }
  2789. function comma(opts) {
  2790. opts = opts || {};
  2791. if (!opts.peek) {
  2792. nobreakcomma(state.tokens.curr, state.tokens.next);
  2793. advance(",");
  2794. } else {
  2795. nobreakcomma(state.tokens.prev, state.tokens.curr);
  2796. }
  2797. // TODO: This is a temporary solution to fight against false-positives in
  2798. // arrays and objects with trailing commas (see GH-363). The best solution
  2799. // would be to extract all whitespace rules out of parser.
  2800. if (state.tokens.next.value !== "]" && state.tokens.next.value !== "}") {
  2801. nonadjacent(state.tokens.curr, state.tokens.next);
  2802. }
  2803. if (state.tokens.next.identifier && !(opts.property && state.option.inES5())) {
  2804. // Keywords that cannot follow a comma operator.
  2805. switch (state.tokens.next.value) {
  2806. case "break":
  2807. case "case":
  2808. case "catch":
  2809. case "continue":
  2810. case "default":
  2811. case "do":
  2812. case "else":
  2813. case "finally":
  2814. case "for":
  2815. case "if":
  2816. case "in":
  2817. case "instanceof":
  2818. case "return":
  2819. case "switch":
  2820. case "throw":
  2821. case "try":
  2822. case "var":
  2823. case "let":
  2824. case "while":
  2825. case "with":
  2826. error("E024", state.tokens.next, state.tokens.next.value);
  2827. return false;
  2828. }
  2829. }
  2830. if (state.tokens.next.type === "(punctuator)") {
  2831. switch (state.tokens.next.value) {
  2832. case "}":
  2833. case "]":
  2834. case ",":
  2835. if (opts.allowTrailing) {
  2836. return true;
  2837. }
  2838. /* falls through */
  2839. case ")":
  2840. error("E024", state.tokens.next, state.tokens.next.value);
  2841. return false;
  2842. }
  2843. }
  2844. return true;
  2845. }
  2846. // Functional constructors for making the symbols that will be inherited by
  2847. // tokens.
  2848. function symbol(s, p) {
  2849. var x = state.syntax[s];
  2850. if (!x || typeof x !== "object") {
  2851. state.syntax[s] = x = {
  2852. id: s,
  2853. lbp: p,
  2854. value: s
  2855. };
  2856. }
  2857. return x;
  2858. }
  2859. function delim(s) {
  2860. return symbol(s, 0);
  2861. }
  2862. function stmt(s, f) {
  2863. var x = delim(s);
  2864. x.identifier = x.reserved = true;
  2865. x.fud = f;
  2866. return x;
  2867. }
  2868. function blockstmt(s, f) {
  2869. var x = stmt(s, f);
  2870. x.block = true;
  2871. return x;
  2872. }
  2873. function reserveName(x) {
  2874. var c = x.id.charAt(0);
  2875. if ((c >= "a" && c <= "z") || (c >= "A" && c <= "Z")) {
  2876. x.identifier = x.reserved = true;
  2877. }
  2878. return x;
  2879. }
  2880. function prefix(s, f) {
  2881. var x = symbol(s, 150);
  2882. reserveName(x);
  2883. x.nud = (typeof f === "function") ? f : function () {
  2884. this.right = expression(150);
  2885. this.arity = "unary";
  2886. if (this.id === "++" || this.id === "--") {
  2887. if (state.option.plusplus) {
  2888. warning("W016", this, this.id);
  2889. } else if ((!this.right.identifier || isReserved(this.right)) &&
  2890. this.right.id !== "." && this.right.id !== "[") {
  2891. warning("W017", this);
  2892. }
  2893. }
  2894. return this;
  2895. };
  2896. return x;
  2897. }
  2898. function type(s, f) {
  2899. var x = delim(s);
  2900. x.type = s;
  2901. x.nud = f;
  2902. return x;
  2903. }
  2904. function reserve(name, func) {
  2905. var x = type(name, func);
  2906. x.identifier = true;
  2907. x.reserved = true;
  2908. return x;
  2909. }
  2910. function FutureReservedWord(name, meta) {
  2911. var x = type(name, (meta && meta.nud) || function () {
  2912. return this;
  2913. });
  2914. meta = meta || {};
  2915. meta.isFutureReservedWord = true;
  2916. x.value = name;
  2917. x.identifier = true;
  2918. x.reserved = true;
  2919. x.meta = meta;
  2920. return x;
  2921. }
  2922. function reservevar(s, v) {
  2923. return reserve(s, function () {
  2924. if (typeof v === "function") {
  2925. v(this);
  2926. }
  2927. return this;
  2928. });
  2929. }
  2930. function infix(s, f, p, w) {
  2931. var x = symbol(s, p);
  2932. reserveName(x);
  2933. x.infix = true;
  2934. x.led = function (left) {
  2935. if (!w) {
  2936. nobreaknonadjacent(state.tokens.prev, state.tokens.curr);
  2937. nonadjacent(state.tokens.curr, state.tokens.next);
  2938. }
  2939. if (s === "in" && left.id === "!") {
  2940. warning("W018", left, "!");
  2941. }
  2942. if (typeof f === "function") {
  2943. return f(left, this);
  2944. } else {
  2945. this.left = left;
  2946. this.right = expression(p);
  2947. return this;
  2948. }
  2949. };
  2950. return x;
  2951. }
  2952. function application(s) {
  2953. var x = symbol(s, 42);
  2954. x.led = function (left) {
  2955. if (!state.option.inESNext()) {
  2956. warning("W104", state.tokens.curr, "arrow function syntax (=>)");
  2957. }
  2958. nobreaknonadjacent(state.tokens.prev, state.tokens.curr);
  2959. nonadjacent(state.tokens.curr, state.tokens.next);
  2960. this.left = left;
  2961. this.right = doFunction(undefined, undefined, false, left);
  2962. return this;
  2963. };
  2964. return x;
  2965. }
  2966. function relation(s, f) {
  2967. var x = symbol(s, 100);
  2968. x.led = function (left) {
  2969. nobreaknonadjacent(state.tokens.prev, state.tokens.curr);
  2970. nonadjacent(state.tokens.curr, state.tokens.next);
  2971. var right = expression(100);
  2972. if (isIdentifier(left, "NaN") || isIdentifier(right, "NaN")) {
  2973. warning("W019", this);
  2974. } else if (f) {
  2975. f.apply(this, [left, right]);
  2976. }
  2977. if (!left || !right) {
  2978. quit("E041", state.tokens.curr.line);
  2979. }
  2980. if (left.id === "!") {
  2981. warning("W018", left, "!");
  2982. }
  2983. if (right.id === "!") {
  2984. warning("W018", right, "!");
  2985. }
  2986. this.left = left;
  2987. this.right = right;
  2988. return this;
  2989. };
  2990. return x;
  2991. }
  2992. function isPoorRelation(node) {
  2993. return node &&
  2994. ((node.type === "(number)" && +node.value === 0) ||
  2995. (node.type === "(string)" && node.value === "") ||
  2996. (node.type === "null" && !state.option.eqnull) ||
  2997. node.type === "true" ||
  2998. node.type === "false" ||
  2999. node.type === "undefined");
  3000. }
  3001. function assignop(s, f, p) {
  3002. var x = infix(s, typeof f === "function" ? f : function (left, that) {
  3003. that.left = left;
  3004. if (left) {
  3005. if (predefined[left.value] === false &&
  3006. scope[left.value]["(global)"] === true) {
  3007. warning("W020", left);
  3008. } else if (left["function"]) {
  3009. warning("W021", left, left.value);
  3010. }
  3011. if (funct[left.value] === "const") {
  3012. error("E013", left, left.value);
  3013. }
  3014. if (left.id === ".") {
  3015. if (!left.left) {
  3016. warning("E031", that);
  3017. } else if (left.left.value === "arguments" && !state.directive["use strict"]) {
  3018. warning("E031", that);
  3019. }
  3020. that.right = expression(10);
  3021. return that;
  3022. } else if (left.id === "[") {
  3023. if (state.tokens.curr.left.first) {
  3024. state.tokens.curr.left.first.forEach(function (t) {
  3025. if (funct[t.value] === "const") {
  3026. error("E013", t, t.value);
  3027. }
  3028. });
  3029. } else if (!left.left) {
  3030. warning("E031", that);
  3031. } else if (left.left.value === "arguments" && !state.directive["use strict"]) {
  3032. warning("E031", that);
  3033. }
  3034. that.right = expression(10);
  3035. return that;
  3036. } else if (left.identifier && !isReserved(left)) {
  3037. if (funct[left.value] === "exception") {
  3038. warning("W022", left);
  3039. }
  3040. that.right = expression(10);
  3041. return that;
  3042. }
  3043. if (left === state.syntax["function"]) {
  3044. warning("W023", state.tokens.curr);
  3045. }
  3046. }
  3047. error("E031", that);
  3048. }, p);
  3049. x.exps = true;
  3050. x.assign = true;
  3051. return x;
  3052. }
  3053. function bitwise(s, f, p) {
  3054. var x = symbol(s, p);
  3055. reserveName(x);
  3056. x.led = (typeof f === "function") ? f : function (left) {
  3057. if (state.option.bitwise) {
  3058. warning("W016", this, this.id);
  3059. }
  3060. this.left = left;
  3061. this.right = expression(p);
  3062. return this;
  3063. };
  3064. return x;
  3065. }
  3066. function bitwiseassignop(s) {
  3067. return assignop(s, function (left, that) {
  3068. if (state.option.bitwise) {
  3069. warning("W016", that, that.id);
  3070. }
  3071. nonadjacent(state.tokens.prev, state.tokens.curr);
  3072. nonadjacent(state.tokens.curr, state.tokens.next);
  3073. if (left) {
  3074. if (left.id === "." || left.id === "[" ||
  3075. (left.identifier && !isReserved(left))) {
  3076. expression(10);
  3077. return that;
  3078. }
  3079. if (left === state.syntax["function"]) {
  3080. warning("W023", state.tokens.curr);
  3081. }
  3082. return that;
  3083. }
  3084. error("E031", that);
  3085. }, 20);
  3086. }
  3087. function suffix(s) {
  3088. var x = symbol(s, 150);
  3089. x.led = function (left) {
  3090. if (state.option.plusplus) {
  3091. warning("W016", this, this.id);
  3092. } else if ((!left.identifier || isReserved(left)) && left.id !== "." && left.id !== "[") {
  3093. warning("W017", this);
  3094. }
  3095. this.left = left;
  3096. return this;
  3097. };
  3098. return x;
  3099. }
  3100. // fnparam means that this identifier is being defined as a function
  3101. // argument (see identifier())
  3102. // prop means that this identifier is that of an object property
  3103. function optionalidentifier(fnparam, prop) {
  3104. if (!state.tokens.next.identifier) {
  3105. return;
  3106. }
  3107. advance();
  3108. var curr = state.tokens.curr;
  3109. var val = state.tokens.curr.value;
  3110. if (!isReserved(curr)) {
  3111. return val;
  3112. }
  3113. if (prop) {
  3114. if (state.option.inES5()) {
  3115. return val;
  3116. }
  3117. }
  3118. if (fnparam && val === "undefined") {
  3119. return val;
  3120. }
  3121. // Display an info message about reserved words as properties
  3122. // and ES5 but do it only once.
  3123. if (prop && !api.getCache("displayed:I002")) {
  3124. api.setCache("displayed:I002", true);
  3125. warning("I002");
  3126. }
  3127. warning("W024", state.tokens.curr, state.tokens.curr.id);
  3128. return val;
  3129. }
  3130. // fnparam means that this identifier is being defined as a function
  3131. // argument
  3132. // prop means that this identifier is that of an object property
  3133. function identifier(fnparam, prop) {
  3134. var i = optionalidentifier(fnparam, prop);
  3135. if (i) {
  3136. return i;
  3137. }
  3138. if (state.tokens.curr.id === "function" && state.tokens.next.id === "(") {
  3139. warning("W025");
  3140. } else {
  3141. error("E030", state.tokens.next, state.tokens.next.value);
  3142. }
  3143. }
  3144. function reachable(s) {
  3145. var i = 0, t;
  3146. if (state.tokens.next.id !== ";" || noreach) {
  3147. return;
  3148. }
  3149. for (;;) {
  3150. t = peek(i);
  3151. if (t.reach) {
  3152. return;
  3153. }
  3154. if (t.id !== "(endline)") {
  3155. if (t.id === "function") {
  3156. if (!state.option.latedef) {
  3157. break;
  3158. }
  3159. warning("W026", t);
  3160. break;
  3161. }
  3162. warning("W027", t, t.value, s);
  3163. break;
  3164. }
  3165. i += 1;
  3166. }
  3167. }
  3168. function statement(noindent) {
  3169. var values;
  3170. var i = indent, r, s = scope, t = state.tokens.next;
  3171. if (t.id === ";") {
  3172. advance(";");
  3173. return;
  3174. }
  3175. // Is this a labelled statement?
  3176. var res = isReserved(t);
  3177. // We're being more tolerant here: if someone uses
  3178. // a FutureReservedWord as a label, we warn but proceed
  3179. // anyway.
  3180. if (res && t.meta && t.meta.isFutureReservedWord && peek().id === ":") {
  3181. warning("W024", t, t.id);
  3182. res = false;
  3183. }
  3184. // detect a destructuring assignment
  3185. if (_.has(["[", "{"], t.value)) {
  3186. if (lookupBlockType().isDestAssign) {
  3187. if (!state.option.inESNext()) {
  3188. warning("W104", state.tokens.curr, "destructuring expression");
  3189. }
  3190. values = destructuringExpression();
  3191. values.forEach(function (tok) {
  3192. isundef(funct, "W117", tok.token, tok.id);
  3193. });
  3194. advance("=");
  3195. destructuringExpressionMatch(values, expression(10, true));
  3196. advance(";");
  3197. return;
  3198. }
  3199. }
  3200. if (t.identifier && !res && peek().id === ":") {
  3201. advance();
  3202. advance(":");
  3203. scope = Object.create(s);
  3204. addlabel(t.value, "label");
  3205. if (!state.tokens.next.labelled && state.tokens.next.value !== "{") {
  3206. warning("W028", state.tokens.next, t.value, state.tokens.next.value);
  3207. }
  3208. state.tokens.next.label = t.value;
  3209. t = state.tokens.next;
  3210. }
  3211. // Is it a lonely block?
  3212. if (t.id === "{") {
  3213. block(true, true);
  3214. return;
  3215. }
  3216. // Parse the statement.
  3217. if (!noindent) {
  3218. indentation();
  3219. }
  3220. r = expression(0, true);
  3221. // Look for the final semicolon.
  3222. if (!t.block) {
  3223. if (!state.option.expr && (!r || !r.exps)) {
  3224. warning("W030", state.tokens.curr);
  3225. } else if (state.option.nonew && r && r.left && r.id === "(" && r.left.id === "new") {
  3226. warning("W031", t);
  3227. }
  3228. if (state.tokens.next.id !== ";") {
  3229. if (!state.option.asi) {
  3230. // If this is the last statement in a block that ends on
  3231. // the same line *and* option lastsemic is on, ignore the warning.
  3232. // Otherwise, complain about missing semicolon.
  3233. if (!state.option.lastsemic || state.tokens.next.id !== "}" ||
  3234. state.tokens.next.line !== state.tokens.curr.line) {
  3235. warningAt("W033", state.tokens.curr.line, state.tokens.curr.character);
  3236. }
  3237. }
  3238. } else {
  3239. adjacent(state.tokens.curr, state.tokens.next);
  3240. advance(";");
  3241. nonadjacent(state.tokens.curr, state.tokens.next);
  3242. }
  3243. }
  3244. // Restore the indentation.
  3245. indent = i;
  3246. scope = s;
  3247. return r;
  3248. }
  3249. function statements(startLine) {
  3250. var a = [], p;
  3251. while (!state.tokens.next.reach && state.tokens.next.id !== "(end)") {
  3252. if (state.tokens.next.id === ";") {
  3253. p = peek();
  3254. if (!p || (p.id !== "(" && p.id !== "[")) {
  3255. warning("W032");
  3256. }
  3257. advance(";");
  3258. } else {
  3259. a.push(statement(startLine === state.tokens.next.line));
  3260. }
  3261. }
  3262. return a;
  3263. }
  3264. /*
  3265. * read all directives
  3266. * recognizes a simple form of asi, but always
  3267. * warns, if it is used
  3268. */
  3269. function directives() {
  3270. var i, p, pn;
  3271. for (;;) {
  3272. if (state.tokens.next.id === "(string)") {
  3273. p = peek(0);
  3274. if (p.id === "(endline)") {
  3275. i = 1;
  3276. do {
  3277. pn = peek(i);
  3278. i = i + 1;
  3279. } while (pn.id === "(endline)");
  3280. if (pn.id !== ";") {
  3281. if (pn.id !== "(string)" && pn.id !== "(number)" &&
  3282. pn.id !== "(regexp)" && pn.identifier !== true &&
  3283. pn.id !== "}") {
  3284. break;
  3285. }
  3286. warning("W033", state.tokens.next);
  3287. } else {
  3288. p = pn;
  3289. }
  3290. } else if (p.id === "}") {
  3291. // Directive with no other statements, warn about missing semicolon
  3292. warning("W033", p);
  3293. } else if (p.id !== ";") {
  3294. break;
  3295. }
  3296. indentation();
  3297. advance();
  3298. if (state.directive[state.tokens.curr.value]) {
  3299. warning("W034", state.tokens.curr, state.tokens.curr.value);
  3300. }
  3301. if (state.tokens.curr.value === "use strict") {
  3302. if (!state.option["(explicitNewcap)"])
  3303. state.option.newcap = true;
  3304. state.option.undef = true;
  3305. }
  3306. // there's no directive negation, so always set to true
  3307. state.directive[state.tokens.curr.value] = true;
  3308. if (p.id === ";") {
  3309. advance(";");
  3310. }
  3311. continue;
  3312. }
  3313. break;
  3314. }
  3315. }
  3316. /*
  3317. * Parses a single block. A block is a sequence of statements wrapped in
  3318. * braces.
  3319. *
  3320. * ordinary - true for everything but function bodies and try blocks.
  3321. * stmt - true if block can be a single statement (e.g. in if/for/while).
  3322. * isfunc - true if block is a function body
  3323. */
  3324. function block(ordinary, stmt, isfunc, isfatarrow) {
  3325. var a,
  3326. b = inblock,
  3327. old_indent = indent,
  3328. m,
  3329. s = scope,
  3330. t,
  3331. line,
  3332. d;
  3333. inblock = ordinary;
  3334. if (!ordinary || !state.option.funcscope)
  3335. scope = Object.create(scope);
  3336. nonadjacent(state.tokens.curr, state.tokens.next);
  3337. t = state.tokens.next;
  3338. var metrics = funct["(metrics)"];
  3339. metrics.nestedBlockDepth += 1;
  3340. metrics.verifyMaxNestedBlockDepthPerFunction();
  3341. if (state.tokens.next.id === "{") {
  3342. advance("{");
  3343. // create a new block scope
  3344. funct["(blockscope)"].stack();
  3345. line = state.tokens.curr.line;
  3346. if (state.tokens.next.id !== "}") {
  3347. indent += state.option.indent;
  3348. while (!ordinary && state.tokens.next.from > indent) {
  3349. indent += state.option.indent;
  3350. }
  3351. if (isfunc) {
  3352. m = {};
  3353. for (d in state.directive) {
  3354. if (_.has(state.directive, d)) {
  3355. m[d] = state.directive[d];
  3356. }
  3357. }
  3358. directives();
  3359. if (state.option.strict && funct["(context)"]["(global)"]) {
  3360. if (!m["use strict"] && !state.directive["use strict"]) {
  3361. warning("E007");
  3362. }
  3363. }
  3364. }
  3365. a = statements(line);
  3366. metrics.statementCount += a.length;
  3367. if (isfunc) {
  3368. state.directive = m;
  3369. }
  3370. indent -= state.option.indent;
  3371. if (line !== state.tokens.next.line) {
  3372. indentation();
  3373. }
  3374. } else if (line !== state.tokens.next.line) {
  3375. indentation();
  3376. }
  3377. advance("}", t);
  3378. funct["(blockscope)"].unstack();
  3379. indent = old_indent;
  3380. } else if (!ordinary) {
  3381. if (isfunc) {
  3382. m = {};
  3383. if (stmt && !isfatarrow && !state.option.inMoz(true)) {
  3384. error("W118", state.tokens.curr, "function closure expressions");
  3385. }
  3386. if (!stmt) {
  3387. for (d in state.directive) {
  3388. if (_.has(state.directive, d)) {
  3389. m[d] = state.directive[d];
  3390. }
  3391. }
  3392. }
  3393. expression(10);
  3394. if (state.option.strict && funct["(context)"]["(global)"]) {
  3395. if (!m["use strict"] && !state.directive["use strict"]) {
  3396. warning("E007");
  3397. }
  3398. }
  3399. } else {
  3400. error("E021", state.tokens.next, "{", state.tokens.next.value);
  3401. }
  3402. } else {
  3403. // check to avoid let declaration not within a block
  3404. funct["(nolet)"] = true;
  3405. if (!stmt || state.option.curly) {
  3406. warning("W116", state.tokens.next, "{", state.tokens.next.value);
  3407. }
  3408. noreach = true;
  3409. indent += state.option.indent;
  3410. // test indentation only if statement is in new line
  3411. a = [statement(state.tokens.next.line === state.tokens.curr.line)];
  3412. indent -= state.option.indent;
  3413. noreach = false;
  3414. delete funct["(nolet)"];
  3415. }
  3416. funct["(verb)"] = null;
  3417. if (!ordinary || !state.option.funcscope) scope = s;
  3418. inblock = b;
  3419. if (ordinary && state.option.noempty && (!a || a.length === 0)) {
  3420. warning("W035");
  3421. }
  3422. metrics.nestedBlockDepth -= 1;
  3423. return a;
  3424. }
  3425. function countMember(m) {
  3426. if (membersOnly && typeof membersOnly[m] !== "boolean") {
  3427. warning("W036", state.tokens.curr, m);
  3428. }
  3429. if (typeof member[m] === "number") {
  3430. member[m] += 1;
  3431. } else {
  3432. member[m] = 1;
  3433. }
  3434. }
  3435. function note_implied(tkn) {
  3436. var name = tkn.value, line = tkn.line, a = implied[name];
  3437. if (typeof a === "function") {
  3438. a = false;
  3439. }
  3440. if (!a) {
  3441. a = [line];
  3442. implied[name] = a;
  3443. } else if (a[a.length - 1] !== line) {
  3444. a.push(line);
  3445. }
  3446. }
  3447. // Build the syntax table by declaring the syntactic elements of the language.
  3448. type("(number)", function () {
  3449. return this;
  3450. });
  3451. type("(string)", function () {
  3452. return this;
  3453. });
  3454. state.syntax["(identifier)"] = {
  3455. type: "(identifier)",
  3456. lbp: 0,
  3457. identifier: true,
  3458. nud: function () {
  3459. var v = this.value,
  3460. s = scope[v],
  3461. f;
  3462. if (typeof s === "function") {
  3463. // Protection against accidental inheritance.
  3464. s = undefined;
  3465. } else if (typeof s === "boolean") {
  3466. f = funct;
  3467. funct = functions[0];
  3468. addlabel(v, "var");
  3469. s = funct;
  3470. funct = f;
  3471. }
  3472. var block;
  3473. if (_.has(funct, "(blockscope)")) {
  3474. block = funct["(blockscope)"].getlabel(v);
  3475. }
  3476. // The name is in scope and defined in the current function.
  3477. if (funct === s || block) {
  3478. // Change 'unused' to 'var', and reject labels.
  3479. // the name is in a block scope
  3480. switch (block ? block[v]["(type)"] : funct[v]) {
  3481. case "unused":
  3482. if (block) block[v]["(type)"] = "var";
  3483. else funct[v] = "var";
  3484. break;
  3485. case "unction":
  3486. if (block) block[v]["(type)"] = "function";
  3487. else funct[v] = "function";
  3488. this["function"] = true;
  3489. break;
  3490. case "function":
  3491. this["function"] = true;
  3492. break;
  3493. case "label":
  3494. warning("W037", state.tokens.curr, v);
  3495. break;
  3496. }
  3497. } else if (funct["(global)"]) {
  3498. // The name is not defined in the function. If we are in the global
  3499. // scope, then we have an undefined variable.
  3500. //
  3501. // Operators typeof and delete do not raise runtime errors even if
  3502. // the base object of a reference is null so no need to display warning
  3503. // if we're inside of typeof or delete.
  3504. if (typeof predefined[v] !== "boolean") {
  3505. // Attempting to subscript a null reference will throw an
  3506. // error, even within the typeof and delete operators
  3507. if (!(anonname === "typeof" || anonname === "delete") ||
  3508. (state.tokens.next && (state.tokens.next.value === "." ||
  3509. state.tokens.next.value === "["))) {
  3510. // if we're in a list comprehension, variables are declared
  3511. // locally and used before being defined. So we check
  3512. // the presence of the given variable in the comp array
  3513. // before declaring it undefined.
  3514. if (!funct["(comparray)"].check(v)) {
  3515. isundef(funct, "W117", state.tokens.curr, v);
  3516. }
  3517. }
  3518. }
  3519. note_implied(state.tokens.curr);
  3520. } else {
  3521. // If the name is already defined in the current
  3522. // function, but not as outer, then there is a scope error.
  3523. switch (funct[v]) {
  3524. case "closure":
  3525. case "function":
  3526. case "var":
  3527. case "unused":
  3528. warning("W038", state.tokens.curr, v);
  3529. break;
  3530. case "label":
  3531. warning("W037", state.tokens.curr, v);
  3532. break;
  3533. case "outer":
  3534. case "global":
  3535. break;
  3536. default:
  3537. // If the name is defined in an outer function, make an outer entry,
  3538. // and if it was unused, make it var.
  3539. if (s === true) {
  3540. funct[v] = true;
  3541. } else if (s === null) {
  3542. warning("W039", state.tokens.curr, v);
  3543. note_implied(state.tokens.curr);
  3544. } else if (typeof s !== "object") {
  3545. // Operators typeof and delete do not raise runtime errors even
  3546. // if the base object of a reference is null so no need to
  3547. //
  3548. // display warning if we're inside of typeof or delete.
  3549. // Attempting to subscript a null reference will throw an
  3550. // error, even within the typeof and delete operators
  3551. if (!(anonname === "typeof" || anonname === "delete") ||
  3552. (state.tokens.next &&
  3553. (state.tokens.next.value === "." || state.tokens.next.value === "["))) {
  3554. isundef(funct, "W117", state.tokens.curr, v);
  3555. }
  3556. funct[v] = true;
  3557. note_implied(state.tokens.curr);
  3558. } else {
  3559. switch (s[v]) {
  3560. case "function":
  3561. case "unction":
  3562. this["function"] = true;
  3563. s[v] = "closure";
  3564. funct[v] = s["(global)"] ? "global" : "outer";
  3565. break;
  3566. case "var":
  3567. case "unused":
  3568. s[v] = "closure";
  3569. funct[v] = s["(global)"] ? "global" : "outer";
  3570. break;
  3571. case "closure":
  3572. funct[v] = s["(global)"] ? "global" : "outer";
  3573. break;
  3574. case "label":
  3575. warning("W037", state.tokens.curr, v);
  3576. }
  3577. }
  3578. }
  3579. }
  3580. return this;
  3581. },
  3582. led: function () {
  3583. error("E033", state.tokens.next, state.tokens.next.value);
  3584. }
  3585. };
  3586. type("(regexp)", function () {
  3587. return this;
  3588. });
  3589. // ECMAScript parser
  3590. delim("(endline)");
  3591. delim("(begin)");
  3592. delim("(end)").reach = true;
  3593. delim("(error)").reach = true;
  3594. delim("}").reach = true;
  3595. delim(")");
  3596. delim("]");
  3597. delim("\"").reach = true;
  3598. delim("'").reach = true;
  3599. delim(";");
  3600. delim(":").reach = true;
  3601. delim("#");
  3602. reserve("else");
  3603. reserve("case").reach = true;
  3604. reserve("catch");
  3605. reserve("default").reach = true;
  3606. reserve("finally");
  3607. reservevar("arguments", function (x) {
  3608. if (state.directive["use strict"] && funct["(global)"]) {
  3609. warning("E008", x);
  3610. }
  3611. });
  3612. reservevar("eval");
  3613. reservevar("false");
  3614. reservevar("Infinity");
  3615. reservevar("null");
  3616. reservevar("this", function (x) {
  3617. if (state.directive["use strict"] && !state.option.validthis && ((funct["(statement)"] &&
  3618. funct["(name)"].charAt(0) > "Z") || funct["(global)"])) {
  3619. warning("W040", x);
  3620. }
  3621. });
  3622. reservevar("true");
  3623. reservevar("undefined");
  3624. assignop("=", "assign", 20);
  3625. assignop("+=", "assignadd", 20);
  3626. assignop("-=", "assignsub", 20);
  3627. assignop("*=", "assignmult", 20);
  3628. assignop("/=", "assigndiv", 20).nud = function () {
  3629. error("E014");
  3630. };
  3631. assignop("%=", "assignmod", 20);
  3632. bitwiseassignop("&=", "assignbitand", 20);
  3633. bitwiseassignop("|=", "assignbitor", 20);
  3634. bitwiseassignop("^=", "assignbitxor", 20);
  3635. bitwiseassignop("<<=", "assignshiftleft", 20);
  3636. bitwiseassignop(">>=", "assignshiftright", 20);
  3637. bitwiseassignop(">>>=", "assignshiftrightunsigned", 20);
  3638. infix(",", function (left, that) {
  3639. var expr;
  3640. that.exprs = [left];
  3641. if (!comma({peek: true})) {
  3642. return that;
  3643. }
  3644. while (true) {
  3645. if (!(expr = expression(10))) {
  3646. break;
  3647. }
  3648. that.exprs.push(expr);
  3649. if (state.tokens.next.value !== "," || !comma()) {
  3650. break;
  3651. }
  3652. }
  3653. return that;
  3654. }, 10, true);
  3655. infix("?", function (left, that) {
  3656. increaseComplexityCount();
  3657. that.left = left;
  3658. that.right = expression(10);
  3659. advance(":");
  3660. that["else"] = expression(10);
  3661. return that;
  3662. }, 30);
  3663. var orPrecendence = 40;
  3664. infix("||", function (left, that) {
  3665. increaseComplexityCount();
  3666. that.left = left;
  3667. that.right = expression(orPrecendence);
  3668. return that;
  3669. }, orPrecendence);
  3670. infix("&&", "and", 50);
  3671. bitwise("|", "bitor", 70);
  3672. bitwise("^", "bitxor", 80);
  3673. bitwise("&", "bitand", 90);
  3674. relation("==", function (left, right) {
  3675. var eqnull = state.option.eqnull && (left.value === "null" || right.value === "null");
  3676. if (!eqnull && state.option.eqeqeq)
  3677. warning("W116", this, "===", "==");
  3678. else if (isPoorRelation(left))
  3679. warning("W041", this, "===", left.value);
  3680. else if (isPoorRelation(right))
  3681. warning("W041", this, "===", right.value);
  3682. return this;
  3683. });
  3684. relation("===");
  3685. relation("!=", function (left, right) {
  3686. var eqnull = state.option.eqnull &&
  3687. (left.value === "null" || right.value === "null");
  3688. if (!eqnull && state.option.eqeqeq) {
  3689. warning("W116", this, "!==", "!=");
  3690. } else if (isPoorRelation(left)) {
  3691. warning("W041", this, "!==", left.value);
  3692. } else if (isPoorRelation(right)) {
  3693. warning("W041", this, "!==", right.value);
  3694. }
  3695. return this;
  3696. });
  3697. relation("!==");
  3698. relation("<");
  3699. relation(">");
  3700. relation("<=");
  3701. relation(">=");
  3702. bitwise("<<", "shiftleft", 120);
  3703. bitwise(">>", "shiftright", 120);
  3704. bitwise(">>>", "shiftrightunsigned", 120);
  3705. infix("in", "in", 120);
  3706. infix("instanceof", "instanceof", 120);
  3707. infix("+", function (left, that) {
  3708. var right = expression(130);
  3709. if (left && right && left.id === "(string)" && right.id === "(string)") {
  3710. left.value += right.value;
  3711. left.character = right.character;
  3712. if (!state.option.scripturl && reg.javascriptURL.test(left.value)) {
  3713. warning("W050", left);
  3714. }
  3715. return left;
  3716. }
  3717. that.left = left;
  3718. that.right = right;
  3719. return that;
  3720. }, 130);
  3721. prefix("+", "num");
  3722. prefix("+++", function () {
  3723. warning("W007");
  3724. this.right = expression(150);
  3725. this.arity = "unary";
  3726. return this;
  3727. });
  3728. infix("+++", function (left) {
  3729. warning("W007");
  3730. this.left = left;
  3731. this.right = expression(130);
  3732. return this;
  3733. }, 130);
  3734. infix("-", "sub", 130);
  3735. prefix("-", "neg");
  3736. prefix("---", function () {
  3737. warning("W006");
  3738. this.right = expression(150);
  3739. this.arity = "unary";
  3740. return this;
  3741. });
  3742. infix("---", function (left) {
  3743. warning("W006");
  3744. this.left = left;
  3745. this.right = expression(130);
  3746. return this;
  3747. }, 130);
  3748. infix("*", "mult", 140);
  3749. infix("/", "div", 140);
  3750. infix("%", "mod", 140);
  3751. suffix("++", "postinc");
  3752. prefix("++", "preinc");
  3753. state.syntax["++"].exps = true;
  3754. suffix("--", "postdec");
  3755. prefix("--", "predec");
  3756. state.syntax["--"].exps = true;
  3757. prefix("delete", function () {
  3758. var p = expression(10);
  3759. if (!p || (p.id !== "." && p.id !== "[")) {
  3760. warning("W051");
  3761. }
  3762. this.first = p;
  3763. return this;
  3764. }).exps = true;
  3765. prefix("~", function () {
  3766. if (state.option.bitwise) {
  3767. warning("W052", this, "~");
  3768. }
  3769. expression(150);
  3770. return this;
  3771. });
  3772. prefix("...", function () {
  3773. if (!state.option.inESNext()) {
  3774. warning("W104", this, "spread/rest operator");
  3775. }
  3776. if (!state.tokens.next.identifier) {
  3777. error("E030", state.tokens.next, state.tokens.next.value);
  3778. }
  3779. expression(150);
  3780. return this;
  3781. });
  3782. prefix("!", function () {
  3783. this.right = expression(150);
  3784. this.arity = "unary";
  3785. if (!this.right) { // '!' followed by nothing? Give up.
  3786. quit("E041", this.line || 0);
  3787. }
  3788. if (bang[this.right.id] === true) {
  3789. warning("W018", this, "!");
  3790. }
  3791. return this;
  3792. });
  3793. prefix("typeof", "typeof");
  3794. prefix("new", function () {
  3795. var c = expression(155), i;
  3796. if (c && c.id !== "function") {
  3797. if (c.identifier) {
  3798. c["new"] = true;
  3799. switch (c.value) {
  3800. case "Number":
  3801. case "String":
  3802. case "Boolean":
  3803. case "Math":
  3804. case "JSON":
  3805. warning("W053", state.tokens.prev, c.value);
  3806. break;
  3807. case "Function":
  3808. if (!state.option.evil) {
  3809. warning("W054");
  3810. }
  3811. break;
  3812. case "Date":
  3813. case "RegExp":
  3814. break;
  3815. default:
  3816. if (c.id !== "function") {
  3817. i = c.value.substr(0, 1);
  3818. if (state.option.newcap && (i < "A" || i > "Z") && !_.has(global, c.value)) {
  3819. warning("W055", state.tokens.curr);
  3820. }
  3821. }
  3822. }
  3823. } else {
  3824. if (c.id !== "." && c.id !== "[" && c.id !== "(") {
  3825. warning("W056", state.tokens.curr);
  3826. }
  3827. }
  3828. } else {
  3829. if (!state.option.supernew)
  3830. warning("W057", this);
  3831. }
  3832. adjacent(state.tokens.curr, state.tokens.next);
  3833. if (state.tokens.next.id !== "(" && !state.option.supernew) {
  3834. warning("W058", state.tokens.curr, state.tokens.curr.value);
  3835. }
  3836. this.first = c;
  3837. return this;
  3838. });
  3839. state.syntax["new"].exps = true;
  3840. prefix("void").exps = true;
  3841. infix(".", function (left, that) {
  3842. adjacent(state.tokens.prev, state.tokens.curr);
  3843. nobreak();
  3844. var m = identifier(false, true);
  3845. if (typeof m === "string") {
  3846. countMember(m);
  3847. }
  3848. that.left = left;
  3849. that.right = m;
  3850. if (m && m === "hasOwnProperty" && state.tokens.next.value === "=") {
  3851. warning("W001");
  3852. }
  3853. if (left && left.value === "arguments" && (m === "callee" || m === "caller")) {
  3854. if (state.option.noarg)
  3855. warning("W059", left, m);
  3856. else if (state.directive["use strict"])
  3857. error("E008");
  3858. } else if (!state.option.evil && left && left.value === "document" &&
  3859. (m === "write" || m === "writeln")) {
  3860. warning("W060", left);
  3861. }
  3862. if (!state.option.evil && (m === "eval" || m === "execScript")) {
  3863. warning("W061");
  3864. }
  3865. return that;
  3866. }, 160, true);
  3867. infix("(", function (left, that) {
  3868. if (state.tokens.prev.id !== "}" && state.tokens.prev.id !== ")") {
  3869. nobreak(state.tokens.prev, state.tokens.curr);
  3870. }
  3871. nospace();
  3872. if (state.option.immed && left && !left.immed && left.id === "function") {
  3873. warning("W062");
  3874. }
  3875. var n = 0;
  3876. var p = [];
  3877. if (left) {
  3878. if (left.type === "(identifier)") {
  3879. if (left.value.match(/^[A-Z]([A-Z0-9_$]*[a-z][A-Za-z0-9_$]*)?$/)) {
  3880. if ("Number String Boolean Date Object".indexOf(left.value) === -1) {
  3881. if (left.value === "Math") {
  3882. warning("W063", left);
  3883. } else if (state.option.newcap) {
  3884. warning("W064", left);
  3885. }
  3886. }
  3887. }
  3888. }
  3889. }
  3890. if (state.tokens.next.id !== ")") {
  3891. for (;;) {
  3892. p[p.length] = expression(10);
  3893. n += 1;
  3894. if (state.tokens.next.id !== ",") {
  3895. break;
  3896. }
  3897. comma();
  3898. }
  3899. }
  3900. advance(")");
  3901. nospace(state.tokens.prev, state.tokens.curr);
  3902. if (typeof left === "object") {
  3903. if (left.value === "parseInt" && n === 1) {
  3904. warning("W065", state.tokens.curr);
  3905. }
  3906. if (!state.option.evil) {
  3907. if (left.value === "eval" || left.value === "Function" ||
  3908. left.value === "execScript") {
  3909. warning("W061", left);
  3910. if (p[0] && [0].id === "(string)") {
  3911. addInternalSrc(left, p[0].value);
  3912. }
  3913. } else if (p[0] && p[0].id === "(string)" &&
  3914. (left.value === "setTimeout" ||
  3915. left.value === "setInterval")) {
  3916. warning("W066", left);
  3917. addInternalSrc(left, p[0].value);
  3918. // window.setTimeout/setInterval
  3919. } else if (p[0] && p[0].id === "(string)" &&
  3920. left.value === "." &&
  3921. left.left.value === "window" &&
  3922. (left.right === "setTimeout" ||
  3923. left.right === "setInterval")) {
  3924. warning("W066", left);
  3925. addInternalSrc(left, p[0].value);
  3926. }
  3927. }
  3928. if (!left.identifier && left.id !== "." && left.id !== "[" &&
  3929. left.id !== "(" && left.id !== "&&" && left.id !== "||" &&
  3930. left.id !== "?") {
  3931. warning("W067", left);
  3932. }
  3933. }
  3934. that.left = left;
  3935. return that;
  3936. }, 155, true).exps = true;
  3937. prefix("(", function () {
  3938. nospace();
  3939. var bracket, brackets = [];
  3940. var pn, pn1, i = 0;
  3941. var ret;
  3942. do {
  3943. pn = peek(i);
  3944. i += 1;
  3945. pn1 = peek(i);
  3946. i += 1;
  3947. } while (pn.value !== ")" && pn1.value !== "=>" && pn1.value !== ";" && pn1.type !== "(end)");
  3948. if (state.tokens.next.id === "function") {
  3949. state.tokens.next.immed = true;
  3950. }
  3951. var exprs = [];
  3952. if (state.tokens.next.id !== ")") {
  3953. for (;;) {
  3954. if (pn1.value === "=>" && state.tokens.next.value === "{") {
  3955. bracket = state.tokens.next;
  3956. bracket.left = destructuringExpression();
  3957. brackets.push(bracket);
  3958. for (var t in bracket.left) {
  3959. exprs.push(bracket.left[t].token);
  3960. }
  3961. } else {
  3962. exprs.push(expression(10));
  3963. }
  3964. if (state.tokens.next.id !== ",") {
  3965. break;
  3966. }
  3967. comma();
  3968. }
  3969. }
  3970. advance(")", this);
  3971. nospace(state.tokens.prev, state.tokens.curr);
  3972. if (state.option.immed && exprs[0] && exprs[0].id === "function") {
  3973. if (state.tokens.next.id !== "(" &&
  3974. (state.tokens.next.id !== "." || (peek().value !== "call" && peek().value !== "apply"))) {
  3975. warning("W068", this);
  3976. }
  3977. }
  3978. if (state.tokens.next.value === "=>") {
  3979. return exprs;
  3980. }
  3981. if (!exprs.length) {
  3982. return;
  3983. }
  3984. if (exprs.length > 1) {
  3985. ret = Object.create(state.syntax[","]);
  3986. ret.exprs = exprs;
  3987. } else {
  3988. ret = exprs[0];
  3989. }
  3990. if (ret) {
  3991. ret.paren = true;
  3992. }
  3993. return ret;
  3994. });
  3995. application("=>");
  3996. infix("[", function (left, that) {
  3997. nobreak(state.tokens.prev, state.tokens.curr);
  3998. nospace();
  3999. var e = expression(10), s;
  4000. if (e && e.type === "(string)") {
  4001. if (!state.option.evil && (e.value === "eval" || e.value === "execScript")) {
  4002. warning("W061", that);
  4003. }
  4004. countMember(e.value);
  4005. if (!state.option.sub && reg.identifier.test(e.value)) {
  4006. s = state.syntax[e.value];
  4007. if (!s || !isReserved(s)) {
  4008. warning("W069", state.tokens.prev, e.value);
  4009. }
  4010. }
  4011. }
  4012. advance("]", that);
  4013. if (e && e.value === "hasOwnProperty" && state.tokens.next.value === "=") {
  4014. warning("W001");
  4015. }
  4016. nospace(state.tokens.prev, state.tokens.curr);
  4017. that.left = left;
  4018. that.right = e;
  4019. return that;
  4020. }, 160, true);
  4021. function comprehensiveArrayExpression() {
  4022. var res = {};
  4023. res.exps = true;
  4024. funct["(comparray)"].stack();
  4025. res.right = expression(10);
  4026. advance("for");
  4027. if (state.tokens.next.value === "each") {
  4028. advance("each");
  4029. if (!state.option.inMoz(true)) {
  4030. warning("W118", state.tokens.curr, "for each");
  4031. }
  4032. }
  4033. advance("(");
  4034. funct["(comparray)"].setState("define");
  4035. res.left = expression(10);
  4036. advance(")");
  4037. if (state.tokens.next.value === "if") {
  4038. advance("if");
  4039. advance("(");
  4040. funct["(comparray)"].setState("filter");
  4041. res.filter = expression(10);
  4042. advance(")");
  4043. }
  4044. advance("]");
  4045. funct["(comparray)"].unstack();
  4046. return res;
  4047. }
  4048. prefix("[", function () {
  4049. var blocktype = lookupBlockType(true);
  4050. if (blocktype.isCompArray) {
  4051. if (!state.option.inMoz(true)) {
  4052. warning("W118", state.tokens.curr, "array comprehension");
  4053. }
  4054. return comprehensiveArrayExpression();
  4055. } else if (blocktype.isDestAssign && !state.option.inESNext()) {
  4056. warning("W104", state.tokens.curr, "destructuring assignment");
  4057. }
  4058. var b = state.tokens.curr.line !== state.tokens.next.line;
  4059. this.first = [];
  4060. if (b) {
  4061. indent += state.option.indent;
  4062. if (state.tokens.next.from === indent + state.option.indent) {
  4063. indent += state.option.indent;
  4064. }
  4065. }
  4066. while (state.tokens.next.id !== "(end)") {
  4067. while (state.tokens.next.id === ",") {
  4068. if (!state.option.inES5())
  4069. warning("W070");
  4070. advance(",");
  4071. }
  4072. if (state.tokens.next.id === "]") {
  4073. break;
  4074. }
  4075. if (b && state.tokens.curr.line !== state.tokens.next.line) {
  4076. indentation();
  4077. }
  4078. this.first.push(expression(10));
  4079. if (state.tokens.next.id === ",") {
  4080. comma({ allowTrailing: true });
  4081. if (state.tokens.next.id === "]" && !state.option.inES5(true)) {
  4082. warning("W070", state.tokens.curr);
  4083. break;
  4084. }
  4085. } else {
  4086. break;
  4087. }
  4088. }
  4089. if (b) {
  4090. indent -= state.option.indent;
  4091. indentation();
  4092. }
  4093. advance("]", this);
  4094. return this;
  4095. }, 160);
  4096. function property_name() {
  4097. var id = optionalidentifier(false, true);
  4098. if (!id) {
  4099. if (state.tokens.next.id === "(string)") {
  4100. id = state.tokens.next.value;
  4101. advance();
  4102. } else if (state.tokens.next.id === "(number)") {
  4103. id = state.tokens.next.value.toString();
  4104. advance();
  4105. }
  4106. }
  4107. if (id === "hasOwnProperty") {
  4108. warning("W001");
  4109. }
  4110. return id;
  4111. }
  4112. function functionparams(parsed) {
  4113. var curr, next;
  4114. var params = [];
  4115. var ident;
  4116. var tokens = [];
  4117. var t;
  4118. var pastDefault = false;
  4119. if (parsed) {
  4120. if (parsed instanceof Array) {
  4121. for (var i in parsed) {
  4122. curr = parsed[i];
  4123. if (_.contains(["{", "["], curr.id)) {
  4124. for (t in curr.left) {
  4125. t = tokens[t];
  4126. if (t.id) {
  4127. params.push(t.id);
  4128. addlabel(t.id, "unused", t.token);
  4129. }
  4130. }
  4131. } else if (curr.value === "...") {
  4132. if (!state.option.inESNext()) {
  4133. warning("W104", curr, "spread/rest operator");
  4134. }
  4135. continue;
  4136. } else {
  4137. addlabel(curr.value, "unused", curr);
  4138. }
  4139. }
  4140. return params;
  4141. } else {
  4142. if (parsed.identifier === true) {
  4143. addlabel(parsed.value, "unused", parsed);
  4144. return [parsed];
  4145. }
  4146. }
  4147. }
  4148. next = state.tokens.next;
  4149. advance("(");
  4150. nospace();
  4151. if (state.tokens.next.id === ")") {
  4152. advance(")");
  4153. return;
  4154. }
  4155. for (;;) {
  4156. if (_.contains(["{", "["], state.tokens.next.id)) {
  4157. tokens = destructuringExpression();
  4158. for (t in tokens) {
  4159. t = tokens[t];
  4160. if (t.id) {
  4161. params.push(t.id);
  4162. addlabel(t.id, "unused", t.token);
  4163. }
  4164. }
  4165. } else if (state.tokens.next.value === "...") {
  4166. if (!state.option.inESNext()) {
  4167. warning("W104", state.tokens.next, "spread/rest operator");
  4168. }
  4169. advance("...");
  4170. nospace();
  4171. ident = identifier(true);
  4172. params.push(ident);
  4173. addlabel(ident, "unused", state.tokens.curr);
  4174. } else {
  4175. ident = identifier(true);
  4176. params.push(ident);
  4177. addlabel(ident, "unused", state.tokens.curr);
  4178. }
  4179. // it is a syntax error to have a regular argument after a default argument
  4180. if (pastDefault) {
  4181. if (state.tokens.next.id !== "=") {
  4182. error("E051", state.tokens.current);
  4183. }
  4184. }
  4185. if (state.tokens.next.id === "=") {
  4186. if (!state.option.inESNext()) {
  4187. warning("W119", state.tokens.next, "default parameters");
  4188. }
  4189. advance("=");
  4190. pastDefault = true;
  4191. expression(10);
  4192. }
  4193. if (state.tokens.next.id === ",") {
  4194. comma();
  4195. } else {
  4196. advance(")", next);
  4197. nospace(state.tokens.prev, state.tokens.curr);
  4198. return params;
  4199. }
  4200. }
  4201. }
  4202. function doFunction(name, statement, generator, fatarrowparams) {
  4203. var f;
  4204. var oldOption = state.option;
  4205. var oldIgnored = state.ignored;
  4206. var oldScope = scope;
  4207. state.option = Object.create(state.option);
  4208. state.ignored = Object.create(state.ignored);
  4209. scope = Object.create(scope);
  4210. funct = {
  4211. "(name)" : name || "\"" + anonname + "\"",
  4212. "(line)" : state.tokens.next.line,
  4213. "(character)" : state.tokens.next.character,
  4214. "(context)" : funct,
  4215. "(breakage)" : 0,
  4216. "(loopage)" : 0,
  4217. "(metrics)" : createMetrics(state.tokens.next),
  4218. "(scope)" : scope,
  4219. "(statement)" : statement,
  4220. "(tokens)" : {},
  4221. "(blockscope)": funct["(blockscope)"],
  4222. "(comparray)" : funct["(comparray)"]
  4223. };
  4224. if (generator) {
  4225. funct["(generator)"] = true;
  4226. }
  4227. f = funct;
  4228. state.tokens.curr.funct = funct;
  4229. functions.push(funct);
  4230. if (name) {
  4231. addlabel(name, "function");
  4232. }
  4233. funct["(params)"] = functionparams(fatarrowparams);
  4234. funct["(metrics)"].verifyMaxParametersPerFunction(funct["(params)"]);
  4235. block(false, true, true, fatarrowparams ? true:false);
  4236. if (generator && funct["(generator)"] !== "yielded") {
  4237. error("E047", state.tokens.curr);
  4238. }
  4239. funct["(metrics)"].verifyMaxStatementsPerFunction();
  4240. funct["(metrics)"].verifyMaxComplexityPerFunction();
  4241. funct["(unusedOption)"] = state.option.unused;
  4242. scope = oldScope;
  4243. state.option = oldOption;
  4244. state.ignored = oldIgnored;
  4245. funct["(last)"] = state.tokens.curr.line;
  4246. funct["(lastcharacter)"] = state.tokens.curr.character;
  4247. funct = funct["(context)"];
  4248. return f;
  4249. }
  4250. function createMetrics(functionStartToken) {
  4251. return {
  4252. statementCount: 0,
  4253. nestedBlockDepth: -1,
  4254. ComplexityCount: 1,
  4255. verifyMaxStatementsPerFunction: function () {
  4256. if (state.option.maxstatements &&
  4257. this.statementCount > state.option.maxstatements) {
  4258. warning("W071", functionStartToken, this.statementCount);
  4259. }
  4260. },
  4261. verifyMaxParametersPerFunction: function (params) {
  4262. params = params || [];
  4263. if (state.option.maxparams && params.length > state.option.maxparams) {
  4264. warning("W072", functionStartToken, params.length);
  4265. }
  4266. },
  4267. verifyMaxNestedBlockDepthPerFunction: function () {
  4268. if (state.option.maxdepth &&
  4269. this.nestedBlockDepth > 0 &&
  4270. this.nestedBlockDepth === state.option.maxdepth + 1) {
  4271. warning("W073", null, this.nestedBlockDepth);
  4272. }
  4273. },
  4274. verifyMaxComplexityPerFunction: function () {
  4275. var max = state.option.maxcomplexity;
  4276. var cc = this.ComplexityCount;
  4277. if (max && cc > max) {
  4278. warning("W074", functionStartToken, cc);
  4279. }
  4280. }
  4281. };
  4282. }
  4283. function increaseComplexityCount() {
  4284. funct["(metrics)"].ComplexityCount += 1;
  4285. }
  4286. // Parse assignments that were found instead of conditionals.
  4287. // For example: if (a = 1) { ... }
  4288. function checkCondAssignment(expr) {
  4289. var id, paren;
  4290. if (expr) {
  4291. id = expr.id;
  4292. paren = expr.paren;
  4293. if (id === "," && (expr = expr.exprs[expr.exprs.length - 1])) {
  4294. id = expr.id;
  4295. paren = paren || expr.paren;
  4296. }
  4297. }
  4298. switch (id) {
  4299. case "=":
  4300. case "+=":
  4301. case "-=":
  4302. case "*=":
  4303. case "%=":
  4304. case "&=":
  4305. case "|=":
  4306. case "^=":
  4307. case "/=":
  4308. if (!paren && !state.option.boss) {
  4309. warning("W084");
  4310. }
  4311. }
  4312. }
  4313. (function (x) {
  4314. x.nud = function (isclassdef) {
  4315. var b, f, i, p, t, g;
  4316. var props = {}; // All properties, including accessors
  4317. var tag = "";
  4318. function saveProperty(name, tkn) {
  4319. if (props[name] && _.has(props, name))
  4320. warning("W075", state.tokens.next, i);
  4321. else
  4322. props[name] = {};
  4323. props[name].basic = true;
  4324. props[name].basictkn = tkn;
  4325. }
  4326. function saveSetter(name, tkn) {
  4327. if (props[name] && _.has(props, name)) {
  4328. if (props[name].basic || props[name].setter)
  4329. warning("W075", state.tokens.next, i);
  4330. } else {
  4331. props[name] = {};
  4332. }
  4333. props[name].setter = true;
  4334. props[name].setterToken = tkn;
  4335. }
  4336. function saveGetter(name) {
  4337. if (props[name] && _.has(props, name)) {
  4338. if (props[name].basic || props[name].getter)
  4339. warning("W075", state.tokens.next, i);
  4340. } else {
  4341. props[name] = {};
  4342. }
  4343. props[name].getter = true;
  4344. props[name].getterToken = state.tokens.curr;
  4345. }
  4346. b = state.tokens.curr.line !== state.tokens.next.line;
  4347. if (b) {
  4348. indent += state.option.indent;
  4349. if (state.tokens.next.from === indent + state.option.indent) {
  4350. indent += state.option.indent;
  4351. }
  4352. }
  4353. for (;;) {
  4354. if (state.tokens.next.id === "}") {
  4355. break;
  4356. }
  4357. if (b) {
  4358. indentation();
  4359. }
  4360. if (isclassdef && state.tokens.next.value === "static") {
  4361. advance("static");
  4362. tag = "static ";
  4363. }
  4364. if (state.tokens.next.value === "get" && peek().id !== ":") {
  4365. advance("get");
  4366. if (!state.option.inES5(!isclassdef)) {
  4367. error("E034");
  4368. }
  4369. i = property_name();
  4370. if (!i) {
  4371. error("E035");
  4372. }
  4373. // It is a Syntax Error if PropName of MethodDefinition is
  4374. // "constructor" and SpecialMethod of MethodDefinition is true.
  4375. if (isclassdef && i === "constructor") {
  4376. error("E049", state.tokens.next, "class getter method", i);
  4377. }
  4378. saveGetter(tag + i);
  4379. t = state.tokens.next;
  4380. adjacent(state.tokens.curr, state.tokens.next);
  4381. f = doFunction();
  4382. p = f["(params)"];
  4383. if (p) {
  4384. warning("W076", t, p[0], i);
  4385. }
  4386. adjacent(state.tokens.curr, state.tokens.next);
  4387. } else if (state.tokens.next.value === "set" && peek().id !== ":") {
  4388. advance("set");
  4389. if (!state.option.inES5(!isclassdef)) {
  4390. error("E034");
  4391. }
  4392. i = property_name();
  4393. if (!i) {
  4394. error("E035");
  4395. }
  4396. // It is a Syntax Error if PropName of MethodDefinition is
  4397. // "constructor" and SpecialMethod of MethodDefinition is true.
  4398. if (isclassdef && i === "constructor") {
  4399. error("E049", state.tokens.next, "class setter method", i);
  4400. }
  4401. saveSetter(tag + i, state.tokens.next);
  4402. t = state.tokens.next;
  4403. adjacent(state.tokens.curr, state.tokens.next);
  4404. f = doFunction();
  4405. p = f["(params)"];
  4406. if (!p || p.length !== 1) {
  4407. warning("W077", t, i);
  4408. }
  4409. } else {
  4410. g = false;
  4411. if (state.tokens.next.value === "*" && state.tokens.next.type === "(punctuator)") {
  4412. if (!state.option.inESNext()) {
  4413. warning("W104", state.tokens.next, "generator functions");
  4414. }
  4415. advance("*");
  4416. g = true;
  4417. }
  4418. i = property_name();
  4419. saveProperty(tag + i, state.tokens.next);
  4420. if (typeof i !== "string") {
  4421. break;
  4422. }
  4423. if (state.tokens.next.value === "(") {
  4424. if (!state.option.inESNext()) {
  4425. warning("W104", state.tokens.curr, "concise methods");
  4426. }
  4427. doFunction(i, undefined, g);
  4428. } else if (!isclassdef) {
  4429. advance(":");
  4430. nonadjacent(state.tokens.curr, state.tokens.next);
  4431. expression(10);
  4432. }
  4433. }
  4434. // It is a Syntax Error if PropName of MethodDefinition is "prototype".
  4435. if (isclassdef && i === "prototype") {
  4436. error("E049", state.tokens.next, "class method", i);
  4437. }
  4438. countMember(i);
  4439. if (isclassdef) {
  4440. tag = "";
  4441. continue;
  4442. }
  4443. if (state.tokens.next.id === ",") {
  4444. comma({ allowTrailing: true, property: true });
  4445. if (state.tokens.next.id === ",") {
  4446. warning("W070", state.tokens.curr);
  4447. } else if (state.tokens.next.id === "}" && !state.option.inES5(true)) {
  4448. warning("W070", state.tokens.curr);
  4449. }
  4450. } else {
  4451. break;
  4452. }
  4453. }
  4454. if (b) {
  4455. indent -= state.option.indent;
  4456. indentation();
  4457. }
  4458. advance("}", this);
  4459. // Check for lonely setters if in the ES5 mode.
  4460. if (state.option.inES5()) {
  4461. for (var name in props) {
  4462. if (_.has(props, name) && props[name].setter && !props[name].getter) {
  4463. warning("W078", props[name].setterToken);
  4464. }
  4465. }
  4466. }
  4467. return this;
  4468. };
  4469. x.fud = function () {
  4470. error("E036", state.tokens.curr);
  4471. };
  4472. }(delim("{")));
  4473. function destructuringExpression() {
  4474. var id, ids;
  4475. var identifiers = [];
  4476. if (!state.option.inESNext()) {
  4477. warning("W104", state.tokens.curr, "destructuring expression");
  4478. }
  4479. var nextInnerDE = function () {
  4480. var ident;
  4481. if (_.contains(["[", "{"], state.tokens.next.value)) {
  4482. ids = destructuringExpression();
  4483. for (var id in ids) {
  4484. id = ids[id];
  4485. identifiers.push({ id: id.id, token: id.token });
  4486. }
  4487. } else if (state.tokens.next.value === ",") {
  4488. identifiers.push({ id: null, token: state.tokens.curr });
  4489. } else {
  4490. ident = identifier();
  4491. if (ident)
  4492. identifiers.push({ id: ident, token: state.tokens.curr });
  4493. }
  4494. };
  4495. if (state.tokens.next.value === "[") {
  4496. advance("[");
  4497. nextInnerDE();
  4498. while (state.tokens.next.value !== "]") {
  4499. advance(",");
  4500. nextInnerDE();
  4501. }
  4502. advance("]");
  4503. } else if (state.tokens.next.value === "{") {
  4504. advance("{");
  4505. id = identifier();
  4506. if (state.tokens.next.value === ":") {
  4507. advance(":");
  4508. nextInnerDE();
  4509. } else {
  4510. identifiers.push({ id: id, token: state.tokens.curr });
  4511. }
  4512. while (state.tokens.next.value !== "}") {
  4513. advance(",");
  4514. id = identifier();
  4515. if (state.tokens.next.value === ":") {
  4516. advance(":");
  4517. nextInnerDE();
  4518. } else {
  4519. identifiers.push({ id: id, token: state.tokens.curr });
  4520. }
  4521. }
  4522. advance("}");
  4523. }
  4524. return identifiers;
  4525. }
  4526. function destructuringExpressionMatch(tokens, value) {
  4527. if (value.first) {
  4528. _.zip(tokens, value.first).forEach(function (val) {
  4529. var token = val[0];
  4530. var value = val[1];
  4531. if (token && value) {
  4532. token.first = value;
  4533. } else if (token && token.first && !value) {
  4534. warning("W080", token.first, token.first.value);
  4535. } /* else {
  4536. XXX value is discarded: wouldn't it need a warning ?
  4537. } */
  4538. });
  4539. }
  4540. }
  4541. var conststatement = stmt("const", function (prefix) {
  4542. var tokens, value;
  4543. // state variable to know if it is a lone identifier, or a destructuring statement.
  4544. var lone;
  4545. if (!state.option.inESNext()) {
  4546. warning("W104", state.tokens.curr, "const");
  4547. }
  4548. this.first = [];
  4549. for (;;) {
  4550. var names = [];
  4551. nonadjacent(state.tokens.curr, state.tokens.next);
  4552. if (_.contains(["{", "["], state.tokens.next.value)) {
  4553. tokens = destructuringExpression();
  4554. lone = false;
  4555. } else {
  4556. tokens = [ { id: identifier(), token: state.tokens.curr } ];
  4557. lone = true;
  4558. }
  4559. for (var t in tokens) {
  4560. t = tokens[t];
  4561. if (funct[t.id] === "const") {
  4562. warning("E011", null, t.id);
  4563. }
  4564. if (funct["(global)"] && predefined[t.id] === false) {
  4565. warning("W079", t.token, t.id);
  4566. }
  4567. if (t.id) {
  4568. addlabel(t.id, "const");
  4569. names.push(t.token);
  4570. }
  4571. }
  4572. if (prefix) {
  4573. break;
  4574. }
  4575. this.first = this.first.concat(names);
  4576. if (state.tokens.next.id !== "=") {
  4577. warning("E012", state.tokens.curr, state.tokens.curr.value);
  4578. }
  4579. if (state.tokens.next.id === "=") {
  4580. nonadjacent(state.tokens.curr, state.tokens.next);
  4581. advance("=");
  4582. nonadjacent(state.tokens.curr, state.tokens.next);
  4583. if (state.tokens.next.id === "undefined") {
  4584. warning("W080", state.tokens.prev, state.tokens.prev.value);
  4585. }
  4586. if (peek(0).id === "=" && state.tokens.next.identifier) {
  4587. warning("W120", state.tokens.next, state.tokens.next.value);
  4588. }
  4589. value = expression(10);
  4590. if (lone) {
  4591. tokens[0].first = value;
  4592. } else {
  4593. destructuringExpressionMatch(names, value);
  4594. }
  4595. }
  4596. if (state.tokens.next.id !== ",") {
  4597. break;
  4598. }
  4599. comma();
  4600. }
  4601. return this;
  4602. });
  4603. conststatement.exps = true;
  4604. var varstatement = stmt("var", function (prefix) {
  4605. // JavaScript does not have block scope. It only has function scope. So,
  4606. // declaring a variable in a block can have unexpected consequences.
  4607. var tokens, lone, value;
  4608. if (funct["(onevar)"] && state.option.onevar) {
  4609. warning("W081");
  4610. } else if (!funct["(global)"]) {
  4611. funct["(onevar)"] = true;
  4612. }
  4613. this.first = [];
  4614. for (;;) {
  4615. var names = [];
  4616. nonadjacent(state.tokens.curr, state.tokens.next);
  4617. if (_.contains(["{", "["], state.tokens.next.value)) {
  4618. tokens = destructuringExpression();
  4619. lone = false;
  4620. } else {
  4621. tokens = [ { id: identifier(), token: state.tokens.curr } ];
  4622. lone = true;
  4623. }
  4624. for (var t in tokens) {
  4625. t = tokens[t];
  4626. if (state.option.inESNext() && funct[t.id] === "const") {
  4627. warning("E011", null, t.id);
  4628. }
  4629. if (funct["(global)"] && predefined[t.id] === false) {
  4630. warning("W079", t.token, t.id);
  4631. }
  4632. if (t.id) {
  4633. addlabel(t.id, "unused", t.token);
  4634. names.push(t.token);
  4635. }
  4636. }
  4637. if (prefix) {
  4638. break;
  4639. }
  4640. this.first = this.first.concat(names);
  4641. if (state.tokens.next.id === "=") {
  4642. nonadjacent(state.tokens.curr, state.tokens.next);
  4643. advance("=");
  4644. nonadjacent(state.tokens.curr, state.tokens.next);
  4645. if (state.tokens.next.id === "undefined") {
  4646. warning("W080", state.tokens.prev, state.tokens.prev.value);
  4647. }
  4648. if (peek(0).id === "=" && state.tokens.next.identifier) {
  4649. warning("W120", state.tokens.next, state.tokens.next.value);
  4650. }
  4651. value = expression(10);
  4652. if (lone) {
  4653. tokens[0].first = value;
  4654. } else {
  4655. destructuringExpressionMatch(names, value);
  4656. }
  4657. }
  4658. if (state.tokens.next.id !== ",") {
  4659. break;
  4660. }
  4661. comma();
  4662. }
  4663. return this;
  4664. });
  4665. varstatement.exps = true;
  4666. var letstatement = stmt("let", function (prefix) {
  4667. var tokens, lone, value, letblock;
  4668. if (!state.option.inESNext()) {
  4669. warning("W104", state.tokens.curr, "let");
  4670. }
  4671. if (state.tokens.next.value === "(") {
  4672. if (!state.option.inMoz(true)) {
  4673. warning("W118", state.tokens.next, "let block");
  4674. }
  4675. advance("(");
  4676. funct["(blockscope)"].stack();
  4677. letblock = true;
  4678. } else if (funct["(nolet)"]) {
  4679. error("E048", state.tokens.curr);
  4680. }
  4681. if (funct["(onevar)"] && state.option.onevar) {
  4682. warning("W081");
  4683. } else if (!funct["(global)"]) {
  4684. funct["(onevar)"] = true;
  4685. }
  4686. this.first = [];
  4687. for (;;) {
  4688. var names = [];
  4689. nonadjacent(state.tokens.curr, state.tokens.next);
  4690. if (_.contains(["{", "["], state.tokens.next.value)) {
  4691. tokens = destructuringExpression();
  4692. lone = false;
  4693. } else {
  4694. tokens = [ { id: identifier(), token: state.tokens.curr.value } ];
  4695. lone = true;
  4696. }
  4697. for (var t in tokens) {
  4698. t = tokens[t];
  4699. if (state.option.inESNext() && funct[t.id] === "const") {
  4700. warning("E011", null, t.id);
  4701. }
  4702. if (funct["(global)"] && predefined[t.id] === false) {
  4703. warning("W079", t.token, t.id);
  4704. }
  4705. if (t.id && !funct["(nolet)"]) {
  4706. addlabel(t.id, "unused", t.token, true);
  4707. names.push(t.token);
  4708. }
  4709. }
  4710. if (prefix) {
  4711. break;
  4712. }
  4713. this.first = this.first.concat(names);
  4714. if (state.tokens.next.id === "=") {
  4715. nonadjacent(state.tokens.curr, state.tokens.next);
  4716. advance("=");
  4717. nonadjacent(state.tokens.curr, state.tokens.next);
  4718. if (state.tokens.next.id === "undefined") {
  4719. warning("W080", state.tokens.prev, state.tokens.prev.value);
  4720. }
  4721. if (peek(0).id === "=" && state.tokens.next.identifier) {
  4722. warning("W120", state.tokens.next, state.tokens.next.value);
  4723. }
  4724. value = expression(10);
  4725. if (lone) {
  4726. tokens[0].first = value;
  4727. } else {
  4728. destructuringExpressionMatch(names, value);
  4729. }
  4730. }
  4731. if (state.tokens.next.id !== ",") {
  4732. break;
  4733. }
  4734. comma();
  4735. }
  4736. if (letblock) {
  4737. advance(")");
  4738. block(true, true);
  4739. this.block = true;
  4740. funct["(blockscope)"].unstack();
  4741. }
  4742. return this;
  4743. });
  4744. letstatement.exps = true;
  4745. blockstmt("class", function () {
  4746. return classdef.call(this, true);
  4747. });
  4748. function classdef(stmt) {
  4749. /*jshint validthis:true */
  4750. if (!state.option.inESNext()) {
  4751. warning("W104", state.tokens.curr, "class");
  4752. }
  4753. if (stmt) {
  4754. // BindingIdentifier
  4755. this.name = identifier();
  4756. addlabel(this.name, "unused", state.tokens.curr);
  4757. } else if (state.tokens.next.identifier && state.tokens.next.value !== "extends") {
  4758. // BindingIdentifier(opt)
  4759. this.name = identifier();
  4760. }
  4761. classtail(this);
  4762. return this;
  4763. }
  4764. function classtail(c) {
  4765. var strictness = state.directive["use strict"];
  4766. // ClassHeritage(opt)
  4767. if (state.tokens.next.value === "extends") {
  4768. advance("extends");
  4769. c.heritage = expression(10);
  4770. }
  4771. // A ClassBody is always strict code.
  4772. state.directive["use strict"] = true;
  4773. advance("{");
  4774. // ClassBody(opt)
  4775. c.body = state.syntax["{"].nud(true);
  4776. state.directive["use strict"] = strictness;
  4777. }
  4778. blockstmt("function", function () {
  4779. var generator = false;
  4780. if (state.tokens.next.value === "*") {
  4781. advance("*");
  4782. if (state.option.inESNext(true)) {
  4783. generator = true;
  4784. } else {
  4785. warning("W119", state.tokens.curr, "function*");
  4786. }
  4787. }
  4788. if (inblock) {
  4789. warning("W082", state.tokens.curr);
  4790. }
  4791. var i = identifier();
  4792. if (funct[i] === "const") {
  4793. warning("E011", null, i);
  4794. }
  4795. adjacent(state.tokens.curr, state.tokens.next);
  4796. addlabel(i, "unction", state.tokens.curr);
  4797. doFunction(i, { statement: true }, generator);
  4798. if (state.tokens.next.id === "(" && state.tokens.next.line === state.tokens.curr.line) {
  4799. error("E039");
  4800. }
  4801. return this;
  4802. });
  4803. prefix("function", function () {
  4804. var generator = false;
  4805. if (state.tokens.next.value === "*") {
  4806. if (!state.option.inESNext()) {
  4807. warning("W119", state.tokens.curr, "function*");
  4808. }
  4809. advance("*");
  4810. generator = true;
  4811. }
  4812. var i = optionalidentifier();
  4813. if (i || state.option.gcl) {
  4814. adjacent(state.tokens.curr, state.tokens.next);
  4815. } else {
  4816. nonadjacent(state.tokens.curr, state.tokens.next);
  4817. }
  4818. doFunction(i, undefined, generator);
  4819. if (!state.option.loopfunc && funct["(loopage)"]) {
  4820. warning("W083");
  4821. }
  4822. return this;
  4823. });
  4824. blockstmt("if", function () {
  4825. var t = state.tokens.next;
  4826. increaseComplexityCount();
  4827. state.condition = true;
  4828. advance("(");
  4829. nonadjacent(this, t);
  4830. nospace();
  4831. checkCondAssignment(expression(0));
  4832. advance(")", t);
  4833. state.condition = false;
  4834. nospace(state.tokens.prev, state.tokens.curr);
  4835. block(true, true);
  4836. if (state.tokens.next.id === "else") {
  4837. nonadjacent(state.tokens.curr, state.tokens.next);
  4838. advance("else");
  4839. if (state.tokens.next.id === "if" || state.tokens.next.id === "switch") {
  4840. statement(true);
  4841. } else {
  4842. block(true, true);
  4843. }
  4844. }
  4845. return this;
  4846. });
  4847. blockstmt("try", function () {
  4848. var b;
  4849. function doCatch() {
  4850. var oldScope = scope;
  4851. var e;
  4852. advance("catch");
  4853. nonadjacent(state.tokens.curr, state.tokens.next);
  4854. advance("(");
  4855. scope = Object.create(oldScope);
  4856. e = state.tokens.next.value;
  4857. if (state.tokens.next.type !== "(identifier)") {
  4858. e = null;
  4859. warning("E030", state.tokens.next, e);
  4860. }
  4861. advance();
  4862. funct = {
  4863. "(name)" : "(catch)",
  4864. "(line)" : state.tokens.next.line,
  4865. "(character)": state.tokens.next.character,
  4866. "(context)" : funct,
  4867. "(breakage)" : funct["(breakage)"],
  4868. "(loopage)" : funct["(loopage)"],
  4869. "(scope)" : scope,
  4870. "(statement)": false,
  4871. "(metrics)" : createMetrics(state.tokens.next),
  4872. "(catch)" : true,
  4873. "(tokens)" : {},
  4874. "(blockscope)": funct["(blockscope)"],
  4875. "(comparray)": funct["(comparray)"]
  4876. };
  4877. if (e) {
  4878. addlabel(e, "exception");
  4879. }
  4880. if (state.tokens.next.value === "if") {
  4881. if (!state.option.inMoz(true)) {
  4882. warning("W118", state.tokens.curr, "catch filter");
  4883. }
  4884. advance("if");
  4885. expression(0);
  4886. }
  4887. advance(")");
  4888. state.tokens.curr.funct = funct;
  4889. functions.push(funct);
  4890. block(false);
  4891. scope = oldScope;
  4892. funct["(last)"] = state.tokens.curr.line;
  4893. funct["(lastcharacter)"] = state.tokens.curr.character;
  4894. funct = funct["(context)"];
  4895. }
  4896. block(false);
  4897. while (state.tokens.next.id === "catch") {
  4898. increaseComplexityCount();
  4899. if (b && (!state.option.inMoz(true))) {
  4900. warning("W118", state.tokens.next, "multiple catch blocks");
  4901. }
  4902. doCatch();
  4903. b = true;
  4904. }
  4905. if (state.tokens.next.id === "finally") {
  4906. advance("finally");
  4907. block(false);
  4908. return;
  4909. }
  4910. if (!b) {
  4911. error("E021", state.tokens.next, "catch", state.tokens.next.value);
  4912. }
  4913. return this;
  4914. });
  4915. blockstmt("while", function () {
  4916. var t = state.tokens.next;
  4917. funct["(breakage)"] += 1;
  4918. funct["(loopage)"] += 1;
  4919. increaseComplexityCount();
  4920. advance("(");
  4921. nonadjacent(this, t);
  4922. nospace();
  4923. checkCondAssignment(expression(0));
  4924. advance(")", t);
  4925. nospace(state.tokens.prev, state.tokens.curr);
  4926. block(true, true);
  4927. funct["(breakage)"] -= 1;
  4928. funct["(loopage)"] -= 1;
  4929. return this;
  4930. }).labelled = true;
  4931. blockstmt("with", function () {
  4932. var t = state.tokens.next;
  4933. if (state.directive["use strict"]) {
  4934. error("E010", state.tokens.curr);
  4935. } else if (!state.option.withstmt) {
  4936. warning("W085", state.tokens.curr);
  4937. }
  4938. advance("(");
  4939. nonadjacent(this, t);
  4940. nospace();
  4941. expression(0);
  4942. advance(")", t);
  4943. nospace(state.tokens.prev, state.tokens.curr);
  4944. block(true, true);
  4945. return this;
  4946. });
  4947. blockstmt("switch", function () {
  4948. var t = state.tokens.next,
  4949. g = false;
  4950. funct["(breakage)"] += 1;
  4951. advance("(");
  4952. nonadjacent(this, t);
  4953. nospace();
  4954. checkCondAssignment(expression(0));
  4955. advance(")", t);
  4956. nospace(state.tokens.prev, state.tokens.curr);
  4957. nonadjacent(state.tokens.curr, state.tokens.next);
  4958. t = state.tokens.next;
  4959. advance("{");
  4960. nonadjacent(state.tokens.curr, state.tokens.next);
  4961. indent += state.option.indent;
  4962. this.cases = [];
  4963. for (;;) {
  4964. switch (state.tokens.next.id) {
  4965. case "case":
  4966. switch (funct["(verb)"]) {
  4967. case "yield":
  4968. case "break":
  4969. case "case":
  4970. case "continue":
  4971. case "return":
  4972. case "switch":
  4973. case "throw":
  4974. break;
  4975. default:
  4976. // You can tell JSHint that you don't use break intentionally by
  4977. // adding a comment /* falls through */ on a line just before
  4978. // the next `case`.
  4979. if (!reg.fallsThrough.test(state.lines[state.tokens.next.line - 2])) {
  4980. warning("W086", state.tokens.curr, "case");
  4981. }
  4982. }
  4983. indentation(-state.option.indent);
  4984. advance("case");
  4985. this.cases.push(expression(20));
  4986. increaseComplexityCount();
  4987. g = true;
  4988. advance(":");
  4989. funct["(verb)"] = "case";
  4990. break;
  4991. case "default":
  4992. switch (funct["(verb)"]) {
  4993. case "yield":
  4994. case "break":
  4995. case "continue":
  4996. case "return":
  4997. case "throw":
  4998. break;
  4999. default:
  5000. // Do not display a warning if 'default' is the first statement or if
  5001. // there is a special /* falls through */ comment.
  5002. if (this.cases.length) {
  5003. if (!reg.fallsThrough.test(state.lines[state.tokens.next.line - 2])) {
  5004. warning("W086", state.tokens.curr, "default");
  5005. }
  5006. }
  5007. }
  5008. indentation(-state.option.indent);
  5009. advance("default");
  5010. g = true;
  5011. advance(":");
  5012. break;
  5013. case "}":
  5014. indent -= state.option.indent;
  5015. indentation();
  5016. advance("}", t);
  5017. funct["(breakage)"] -= 1;
  5018. funct["(verb)"] = undefined;
  5019. return;
  5020. case "(end)":
  5021. error("E023", state.tokens.next, "}");
  5022. return;
  5023. default:
  5024. if (g) {
  5025. switch (state.tokens.curr.id) {
  5026. case ",":
  5027. error("E040");
  5028. return;
  5029. case ":":
  5030. g = false;
  5031. statements();
  5032. break;
  5033. default:
  5034. error("E025", state.tokens.curr);
  5035. return;
  5036. }
  5037. } else {
  5038. if (state.tokens.curr.id === ":") {
  5039. advance(":");
  5040. error("E024", state.tokens.curr, ":");
  5041. statements();
  5042. } else {
  5043. error("E021", state.tokens.next, "case", state.tokens.next.value);
  5044. return;
  5045. }
  5046. }
  5047. }
  5048. }
  5049. }).labelled = true;
  5050. stmt("debugger", function () {
  5051. if (!state.option.debug) {
  5052. warning("W087");
  5053. }
  5054. return this;
  5055. }).exps = true;
  5056. (function () {
  5057. var x = stmt("do", function () {
  5058. funct["(breakage)"] += 1;
  5059. funct["(loopage)"] += 1;
  5060. increaseComplexityCount();
  5061. this.first = block(true, true);
  5062. advance("while");
  5063. var t = state.tokens.next;
  5064. nonadjacent(state.tokens.curr, t);
  5065. advance("(");
  5066. nospace();
  5067. checkCondAssignment(expression(0));
  5068. advance(")", t);
  5069. nospace(state.tokens.prev, state.tokens.curr);
  5070. funct["(breakage)"] -= 1;
  5071. funct["(loopage)"] -= 1;
  5072. return this;
  5073. });
  5074. x.labelled = true;
  5075. x.exps = true;
  5076. }());
  5077. blockstmt("for", function () {
  5078. var s, t = state.tokens.next;
  5079. var letscope = false;
  5080. var foreachtok = null;
  5081. if (t.value === "each") {
  5082. foreachtok = t;
  5083. advance("each");
  5084. if (!state.option.inMoz(true)) {
  5085. warning("W118", state.tokens.curr, "for each");
  5086. }
  5087. }
  5088. funct["(breakage)"] += 1;
  5089. funct["(loopage)"] += 1;
  5090. increaseComplexityCount();
  5091. advance("(");
  5092. nonadjacent(this, t);
  5093. nospace();
  5094. // what kind of for(…) statement it is? for(…of…)? for(…in…)? for(…;…;…)?
  5095. var nextop; // contains the token of the "in" or "of" operator
  5096. var i = 0;
  5097. var inof = ["in", "of"];
  5098. do {
  5099. nextop = peek(i);
  5100. ++i;
  5101. } while (!_.contains(inof, nextop.value) && nextop.value !== ";" &&
  5102. nextop.type !== "(end)");
  5103. // if we're in a for (… in|of …) statement
  5104. if (_.contains(inof, nextop.value)) {
  5105. if (!state.option.inESNext() && nextop.value === "of") {
  5106. error("W104", nextop, "for of");
  5107. }
  5108. if (state.tokens.next.id === "var") {
  5109. advance("var");
  5110. state.syntax["var"].fud.call(state.syntax["var"].fud, true);
  5111. } else if (state.tokens.next.id === "let") {
  5112. advance("let");
  5113. // create a new block scope
  5114. letscope = true;
  5115. funct["(blockscope)"].stack();
  5116. state.syntax["let"].fud.call(state.syntax["let"].fud, true);
  5117. } else {
  5118. switch (funct[state.tokens.next.value]) {
  5119. case "unused":
  5120. funct[state.tokens.next.value] = "var";
  5121. break;
  5122. case "var":
  5123. break;
  5124. default:
  5125. if (!funct["(blockscope)"].getlabel(state.tokens.next.value))
  5126. warning("W088", state.tokens.next, state.tokens.next.value);
  5127. }
  5128. advance();
  5129. }
  5130. advance(nextop.value);
  5131. expression(20);
  5132. advance(")", t);
  5133. s = block(true, true);
  5134. if (state.option.forin && s && (s.length > 1 || typeof s[0] !== "object" ||
  5135. s[0].value !== "if")) {
  5136. warning("W089", this);
  5137. }
  5138. funct["(breakage)"] -= 1;
  5139. funct["(loopage)"] -= 1;
  5140. } else {
  5141. if (foreachtok) {
  5142. error("E045", foreachtok);
  5143. }
  5144. if (state.tokens.next.id !== ";") {
  5145. if (state.tokens.next.id === "var") {
  5146. advance("var");
  5147. state.syntax["var"].fud.call(state.syntax["var"].fud);
  5148. } else if (state.tokens.next.id === "let") {
  5149. advance("let");
  5150. // create a new block scope
  5151. letscope = true;
  5152. funct["(blockscope)"].stack();
  5153. state.syntax["let"].fud.call(state.syntax["let"].fud);
  5154. } else {
  5155. for (;;) {
  5156. expression(0, "for");
  5157. if (state.tokens.next.id !== ",") {
  5158. break;
  5159. }
  5160. comma();
  5161. }
  5162. }
  5163. }
  5164. nolinebreak(state.tokens.curr);
  5165. advance(";");
  5166. if (state.tokens.next.id !== ";") {
  5167. checkCondAssignment(expression(0));
  5168. }
  5169. nolinebreak(state.tokens.curr);
  5170. advance(";");
  5171. if (state.tokens.next.id === ";") {
  5172. error("E021", state.tokens.next, ")", ";");
  5173. }
  5174. if (state.tokens.next.id !== ")") {
  5175. for (;;) {
  5176. expression(0, "for");
  5177. if (state.tokens.next.id !== ",") {
  5178. break;
  5179. }
  5180. comma();
  5181. }
  5182. }
  5183. advance(")", t);
  5184. nospace(state.tokens.prev, state.tokens.curr);
  5185. block(true, true);
  5186. funct["(breakage)"] -= 1;
  5187. funct["(loopage)"] -= 1;
  5188. }
  5189. // unstack loop blockscope
  5190. if (letscope) {
  5191. funct["(blockscope)"].unstack();
  5192. }
  5193. return this;
  5194. }).labelled = true;
  5195. stmt("break", function () {
  5196. var v = state.tokens.next.value;
  5197. if (funct["(breakage)"] === 0)
  5198. warning("W052", state.tokens.next, this.value);
  5199. if (!state.option.asi)
  5200. nolinebreak(this);
  5201. if (state.tokens.next.id !== ";" && !state.tokens.next.reach) {
  5202. if (state.tokens.curr.line === state.tokens.next.line) {
  5203. if (funct[v] !== "label") {
  5204. warning("W090", state.tokens.next, v);
  5205. } else if (scope[v] !== funct) {
  5206. warning("W091", state.tokens.next, v);
  5207. }
  5208. this.first = state.tokens.next;
  5209. advance();
  5210. }
  5211. }
  5212. reachable("break");
  5213. return this;
  5214. }).exps = true;
  5215. stmt("continue", function () {
  5216. var v = state.tokens.next.value;
  5217. if (funct["(breakage)"] === 0)
  5218. warning("W052", state.tokens.next, this.value);
  5219. if (!state.option.asi)
  5220. nolinebreak(this);
  5221. if (state.tokens.next.id !== ";" && !state.tokens.next.reach) {
  5222. if (state.tokens.curr.line === state.tokens.next.line) {
  5223. if (funct[v] !== "label") {
  5224. warning("W090", state.tokens.next, v);
  5225. } else if (scope[v] !== funct) {
  5226. warning("W091", state.tokens.next, v);
  5227. }
  5228. this.first = state.tokens.next;
  5229. advance();
  5230. }
  5231. } else if (!funct["(loopage)"]) {
  5232. warning("W052", state.tokens.next, this.value);
  5233. }
  5234. reachable("continue");
  5235. return this;
  5236. }).exps = true;
  5237. stmt("return", function () {
  5238. if (this.line === state.tokens.next.line) {
  5239. if (state.tokens.next.id === "(regexp)")
  5240. warning("W092");
  5241. if (state.tokens.next.id !== ";" && !state.tokens.next.reach) {
  5242. nonadjacent(state.tokens.curr, state.tokens.next);
  5243. this.first = expression(0);
  5244. if (this.first &&
  5245. this.first.type === "(punctuator)" && this.first.value === "=" && !state.option.boss) {
  5246. warningAt("W093", this.first.line, this.first.character);
  5247. }
  5248. }
  5249. } else {
  5250. if (state.tokens.next.type === "(punctuator)" &&
  5251. ["[", "{", "+", "-"].indexOf(state.tokens.next.value) > -1) {
  5252. nolinebreak(this); // always warn (Line breaking error)
  5253. }
  5254. }
  5255. reachable("return");
  5256. return this;
  5257. }).exps = true;
  5258. (function (x) {
  5259. x.exps = true;
  5260. x.lbp = 25;
  5261. }(prefix("yield", function () {
  5262. var prev = state.tokens.prev;
  5263. if (state.option.inESNext(true) && !funct["(generator)"]) {
  5264. error("E046", state.tokens.curr, "yield");
  5265. } else if (!state.option.inESNext()) {
  5266. warning("W104", state.tokens.curr, "yield");
  5267. }
  5268. funct["(generator)"] = "yielded";
  5269. if (this.line === state.tokens.next.line || !state.option.inMoz(true)) {
  5270. if (state.tokens.next.id === "(regexp)")
  5271. warning("W092");
  5272. if (state.tokens.next.id !== ";" && !state.tokens.next.reach && state.tokens.next.nud) {
  5273. nobreaknonadjacent(state.tokens.curr, state.tokens.next);
  5274. this.first = expression(10);
  5275. if (this.first.type === "(punctuator)" && this.first.value === "=" && !state.option.boss) {
  5276. warningAt("W093", this.first.line, this.first.character);
  5277. }
  5278. }
  5279. if (state.option.inMoz(true) && state.tokens.next.id !== ")" &&
  5280. (prev.lbp > 30 || (!prev.assign && !isEndOfExpr()) || prev.id === "yield")) {
  5281. error("E050", this);
  5282. }
  5283. } else if (!state.option.asi) {
  5284. nolinebreak(this); // always warn (Line breaking error)
  5285. }
  5286. return this;
  5287. })));
  5288. stmt("throw", function () {
  5289. nolinebreak(this);
  5290. nonadjacent(state.tokens.curr, state.tokens.next);
  5291. this.first = expression(20);
  5292. reachable("throw");
  5293. return this;
  5294. }).exps = true;
  5295. stmt("import", function () {
  5296. if (!state.option.inESNext()) {
  5297. warning("W119", state.tokens.curr, "import");
  5298. }
  5299. if (state.tokens.next.identifier) {
  5300. this.name = identifier();
  5301. addlabel(this.name, "unused", state.tokens.curr);
  5302. } else {
  5303. advance("{");
  5304. for (;;) {
  5305. var importName;
  5306. if (state.tokens.next.type === "default") {
  5307. importName = "default";
  5308. advance("default");
  5309. } else {
  5310. importName = identifier();
  5311. }
  5312. if (state.tokens.next.value === "as") {
  5313. advance("as");
  5314. importName = identifier();
  5315. }
  5316. addlabel(importName, "unused", state.tokens.curr);
  5317. if (state.tokens.next.value === ",") {
  5318. advance(",");
  5319. } else if (state.tokens.next.value === "}") {
  5320. advance("}");
  5321. break;
  5322. } else {
  5323. error("E024", state.tokens.next, state.tokens.next.value);
  5324. break;
  5325. }
  5326. }
  5327. }
  5328. advance("from");
  5329. advance("(string)");
  5330. return this;
  5331. }).exps = true;
  5332. stmt("export", function () {
  5333. if (!state.option.inESNext()) {
  5334. warning("W119", state.tokens.curr, "export");
  5335. }
  5336. if (state.tokens.next.type === "default") {
  5337. advance("default");
  5338. if (state.tokens.next.id === "function" || state.tokens.next.id === "class") {
  5339. this.block = true;
  5340. }
  5341. this.exportee = expression(10);
  5342. return this;
  5343. }
  5344. if (state.tokens.next.value === "{") {
  5345. advance("{");
  5346. for (;;) {
  5347. identifier();
  5348. if (state.tokens.next.value === ",") {
  5349. advance(",");
  5350. } else if (state.tokens.next.value === "}") {
  5351. advance("}");
  5352. break;
  5353. } else {
  5354. error("E024", state.tokens.next, state.tokens.next.value);
  5355. break;
  5356. }
  5357. }
  5358. return this;
  5359. }
  5360. if (state.tokens.next.id === "var") {
  5361. advance("var");
  5362. state.syntax["var"].fud.call(state.syntax["var"].fud);
  5363. } else if (state.tokens.next.id === "let") {
  5364. advance("let");
  5365. state.syntax["let"].fud.call(state.syntax["let"].fud);
  5366. } else if (state.tokens.next.id === "const") {
  5367. advance("const");
  5368. state.syntax["const"].fud.call(state.syntax["const"].fud);
  5369. } else if (state.tokens.next.id === "function") {
  5370. this.block = true;
  5371. advance("function");
  5372. state.syntax["function"].fud();
  5373. } else if (state.tokens.next.id === "class") {
  5374. this.block = true;
  5375. advance("class");
  5376. state.syntax["class"].fud();
  5377. } else {
  5378. error("E024", state.tokens.next, state.tokens.next.value);
  5379. }
  5380. return this;
  5381. }).exps = true;
  5382. // Future Reserved Words
  5383. FutureReservedWord("abstract");
  5384. FutureReservedWord("boolean");
  5385. FutureReservedWord("byte");
  5386. FutureReservedWord("char");
  5387. FutureReservedWord("class", { es5: true, nud: classdef });
  5388. FutureReservedWord("double");
  5389. FutureReservedWord("enum", { es5: true });
  5390. FutureReservedWord("export", { es5: true });
  5391. FutureReservedWord("extends", { es5: true });
  5392. FutureReservedWord("final");
  5393. FutureReservedWord("float");
  5394. FutureReservedWord("goto");
  5395. FutureReservedWord("implements", { es5: true, strictOnly: true });
  5396. FutureReservedWord("import", { es5: true });
  5397. FutureReservedWord("int");
  5398. FutureReservedWord("interface", { es5: true, strictOnly: true });
  5399. FutureReservedWord("long");
  5400. FutureReservedWord("native");
  5401. FutureReservedWord("package", { es5: true, strictOnly: true });
  5402. FutureReservedWord("private", { es5: true, strictOnly: true });
  5403. FutureReservedWord("protected", { es5: true, strictOnly: true });
  5404. FutureReservedWord("public", { es5: true, strictOnly: true });
  5405. FutureReservedWord("short");
  5406. FutureReservedWord("static", { es5: true, strictOnly: true });
  5407. FutureReservedWord("super", { es5: true });
  5408. FutureReservedWord("synchronized");
  5409. FutureReservedWord("throws");
  5410. FutureReservedWord("transient");
  5411. FutureReservedWord("volatile");
  5412. // this function is used to determine wether a squarebracket or a curlybracket
  5413. // expression is a comprehension array, destructuring assignment or a json value.
  5414. var lookupBlockType = function () {
  5415. var pn, pn1;
  5416. var i = 0;
  5417. var bracketStack = 0;
  5418. var ret = {};
  5419. if (_.contains(["[", "{"], state.tokens.curr.value))
  5420. bracketStack += 1;
  5421. if (_.contains(["[", "{"], state.tokens.next.value))
  5422. bracketStack += 1;
  5423. if (_.contains(["]", "}"], state.tokens.next.value))
  5424. bracketStack -= 1;
  5425. do {
  5426. pn = peek(i);
  5427. pn1 = peek(i + 1);
  5428. i = i + 1;
  5429. if (_.contains(["[", "{"], pn.value)) {
  5430. bracketStack += 1;
  5431. } else if (_.contains(["]", "}"], pn.value)) {
  5432. bracketStack -= 1;
  5433. }
  5434. if (pn.identifier && pn.value === "for" && bracketStack === 1) {
  5435. ret.isCompArray = true;
  5436. ret.notJson = true;
  5437. break;
  5438. }
  5439. if (_.contains(["}", "]"], pn.value) && pn1.value === "=") {
  5440. ret.isDestAssign = true;
  5441. ret.notJson = true;
  5442. break;
  5443. }
  5444. if (pn.value === ";") {
  5445. ret.isBlock = true;
  5446. ret.notJson = true;
  5447. }
  5448. } while (bracketStack > 0 && pn.id !== "(end)" && i < 15);
  5449. return ret;
  5450. };
  5451. // Check whether this function has been reached for a destructuring assign with undeclared values
  5452. function destructuringAssignOrJsonValue() {
  5453. // lookup for the assignment (esnext only)
  5454. // if it has semicolons, it is a block, so go parse it as a block
  5455. // or it's not a block, but there are assignments, check for undeclared variables
  5456. var block = lookupBlockType();
  5457. if (block.notJson) {
  5458. if (!state.option.inESNext() && block.isDestAssign) {
  5459. warning("W104", state.tokens.curr, "destructuring assignment");
  5460. }
  5461. statements();
  5462. // otherwise parse json value
  5463. } else {
  5464. state.option.laxbreak = true;
  5465. state.jsonMode = true;
  5466. jsonValue();
  5467. }
  5468. }
  5469. // array comprehension parsing function
  5470. // parses and defines the three states of the list comprehension in order
  5471. // to avoid defining global variables, but keeping them to the list comprehension scope
  5472. // only. The order of the states are as follows:
  5473. // * "use" which will be the returned iterative part of the list comprehension
  5474. // * "define" which will define the variables local to the list comprehension
  5475. // * "filter" which will help filter out values
  5476. var arrayComprehension = function () {
  5477. var CompArray = function () {
  5478. this.mode = "use";
  5479. this.variables = [];
  5480. };
  5481. var _carrays = [];
  5482. var _current;
  5483. function declare(v) {
  5484. var l = _current.variables.filter(function (elt) {
  5485. // if it has, change its undef state
  5486. if (elt.value === v) {
  5487. elt.undef = false;
  5488. return v;
  5489. }
  5490. }).length;
  5491. return l !== 0;
  5492. }
  5493. function use(v) {
  5494. var l = _current.variables.filter(function (elt) {
  5495. // and if it has been defined
  5496. if (elt.value === v && !elt.undef) {
  5497. if (elt.unused === true) {
  5498. elt.unused = false;
  5499. }
  5500. return v;
  5501. }
  5502. }).length;
  5503. // otherwise we warn about it
  5504. return (l === 0);
  5505. }
  5506. return {stack: function () {
  5507. _current = new CompArray();
  5508. _carrays.push(_current);
  5509. },
  5510. unstack: function () {
  5511. _current.variables.filter(function (v) {
  5512. if (v.unused)
  5513. warning("W098", v.token, v.value);
  5514. if (v.undef)
  5515. isundef(v.funct, "W117", v.token, v.value);
  5516. });
  5517. _carrays.splice(_carrays[_carrays.length - 1], 1);
  5518. _current = _carrays[_carrays.length - 1];
  5519. },
  5520. setState: function (s) {
  5521. if (_.contains(["use", "define", "filter"], s))
  5522. _current.mode = s;
  5523. },
  5524. check: function (v) {
  5525. // When we are in "use" state of the list comp, we enqueue that var
  5526. if (_current && _current.mode === "use") {
  5527. _current.variables.push({funct: funct,
  5528. token: state.tokens.curr,
  5529. value: v,
  5530. undef: true,
  5531. unused: false});
  5532. return true;
  5533. // When we are in "define" state of the list comp,
  5534. } else if (_current && _current.mode === "define") {
  5535. // check if the variable has been used previously
  5536. if (!declare(v)) {
  5537. _current.variables.push({funct: funct,
  5538. token: state.tokens.curr,
  5539. value: v,
  5540. undef: false,
  5541. unused: true});
  5542. }
  5543. return true;
  5544. // When we are in "filter" state,
  5545. } else if (_current && _current.mode === "filter") {
  5546. // we check whether current variable has been declared
  5547. if (use(v)) {
  5548. // if not we warn about it
  5549. isundef(funct, "W117", state.tokens.curr, v);
  5550. }
  5551. return true;
  5552. }
  5553. return false;
  5554. }
  5555. };
  5556. };
  5557. // Parse JSON
  5558. function jsonValue() {
  5559. function jsonObject() {
  5560. var o = {}, t = state.tokens.next;
  5561. advance("{");
  5562. if (state.tokens.next.id !== "}") {
  5563. for (;;) {
  5564. if (state.tokens.next.id === "(end)") {
  5565. error("E026", state.tokens.next, t.line);
  5566. } else if (state.tokens.next.id === "}") {
  5567. warning("W094", state.tokens.curr);
  5568. break;
  5569. } else if (state.tokens.next.id === ",") {
  5570. error("E028", state.tokens.next);
  5571. } else if (state.tokens.next.id !== "(string)") {
  5572. warning("W095", state.tokens.next, state.tokens.next.value);
  5573. }
  5574. if (o[state.tokens.next.value] === true) {
  5575. warning("W075", state.tokens.next, state.tokens.next.value);
  5576. } else if ((state.tokens.next.value === "__proto__" &&
  5577. !state.option.proto) || (state.tokens.next.value === "__iterator__" &&
  5578. !state.option.iterator)) {
  5579. warning("W096", state.tokens.next, state.tokens.next.value);
  5580. } else {
  5581. o[state.tokens.next.value] = true;
  5582. }
  5583. advance();
  5584. advance(":");
  5585. jsonValue();
  5586. if (state.tokens.next.id !== ",") {
  5587. break;
  5588. }
  5589. advance(",");
  5590. }
  5591. }
  5592. advance("}");
  5593. }
  5594. function jsonArray() {
  5595. var t = state.tokens.next;
  5596. advance("[");
  5597. if (state.tokens.next.id !== "]") {
  5598. for (;;) {
  5599. if (state.tokens.next.id === "(end)") {
  5600. error("E027", state.tokens.next, t.line);
  5601. } else if (state.tokens.next.id === "]") {
  5602. warning("W094", state.tokens.curr);
  5603. break;
  5604. } else if (state.tokens.next.id === ",") {
  5605. error("E028", state.tokens.next);
  5606. }
  5607. jsonValue();
  5608. if (state.tokens.next.id !== ",") {
  5609. break;
  5610. }
  5611. advance(",");
  5612. }
  5613. }
  5614. advance("]");
  5615. }
  5616. switch (state.tokens.next.id) {
  5617. case "{":
  5618. jsonObject();
  5619. break;
  5620. case "[":
  5621. jsonArray();
  5622. break;
  5623. case "true":
  5624. case "false":
  5625. case "null":
  5626. case "(number)":
  5627. case "(string)":
  5628. advance();
  5629. break;
  5630. case "-":
  5631. advance("-");
  5632. if (state.tokens.curr.character !== state.tokens.next.from) {
  5633. warning("W011", state.tokens.curr);
  5634. }
  5635. adjacent(state.tokens.curr, state.tokens.next);
  5636. advance("(number)");
  5637. break;
  5638. default:
  5639. error("E003", state.tokens.next);
  5640. }
  5641. }
  5642. var blockScope = function () {
  5643. var _current = {};
  5644. var _variables = [_current];
  5645. function _checkBlockLabels() {
  5646. for (var t in _current) {
  5647. if (_current[t]["(type)"] === "unused") {
  5648. if (state.option.unused) {
  5649. var tkn = _current[t]["(token)"];
  5650. var line = tkn.line;
  5651. var chr = tkn.character;
  5652. warningAt("W098", line, chr, t);
  5653. }
  5654. }
  5655. }
  5656. }
  5657. return {
  5658. stack: function () {
  5659. _current = {};
  5660. _variables.push(_current);
  5661. },
  5662. unstack: function () {
  5663. _checkBlockLabels();
  5664. _variables.splice(_variables.length - 1, 1);
  5665. _current = _.last(_variables);
  5666. },
  5667. getlabel: function (l) {
  5668. for (var i = _variables.length - 1 ; i >= 0; --i) {
  5669. if (_.has(_variables[i], l)) {
  5670. return _variables[i];
  5671. }
  5672. }
  5673. },
  5674. current: {
  5675. has: function (t) {
  5676. return _.has(_current, t);
  5677. },
  5678. add: function (t, type, tok) {
  5679. _current[t] = { "(type)" : type,
  5680. "(token)": tok };
  5681. }
  5682. }
  5683. };
  5684. };
  5685. // The actual JSHINT function itself.
  5686. var itself = function (s, o, g) {
  5687. var i, k, x;
  5688. var optionKeys;
  5689. var newOptionObj = {};
  5690. var newIgnoredObj = {};
  5691. state.reset();
  5692. if (o && o.scope) {
  5693. JSHINT.scope = o.scope;
  5694. } else {
  5695. JSHINT.errors = [];
  5696. JSHINT.undefs = [];
  5697. JSHINT.internals = [];
  5698. JSHINT.blacklist = {};
  5699. JSHINT.scope = "(main)";
  5700. }
  5701. predefined = Object.create(null);
  5702. combine(predefined, vars.ecmaIdentifiers);
  5703. combine(predefined, vars.reservedVars);
  5704. combine(predefined, g || {});
  5705. declared = Object.create(null);
  5706. exported = Object.create(null);
  5707. function each(obj, cb) {
  5708. if (!obj)
  5709. return;
  5710. if (!Array.isArray(obj) && typeof obj === "object")
  5711. obj = Object.keys(obj);
  5712. obj.forEach(cb);
  5713. }
  5714. if (o) {
  5715. each(o.predef || null, function (item) {
  5716. var slice, prop;
  5717. if (item[0] === "-") {
  5718. slice = item.slice(1);
  5719. JSHINT.blacklist[slice] = slice;
  5720. } else {
  5721. prop = Object.getOwnPropertyDescriptor(o.predef, item);
  5722. predefined[item] = prop ? prop.value : false;
  5723. }
  5724. });
  5725. each(o.exported || null, function (item) {
  5726. exported[item] = true;
  5727. });
  5728. delete o.predef;
  5729. delete o.exported;
  5730. optionKeys = Object.keys(o);
  5731. for (x = 0; x < optionKeys.length; x++) {
  5732. if (/^-W\d{3}$/g.test(optionKeys[x])) {
  5733. newIgnoredObj[optionKeys[x].slice(1)] = true;
  5734. } else {
  5735. newOptionObj[optionKeys[x]] = o[optionKeys[x]];
  5736. if (optionKeys[x] === "newcap" && o[optionKeys[x]] === false)
  5737. newOptionObj["(explicitNewcap)"] = true;
  5738. if (optionKeys[x] === "indent")
  5739. newOptionObj["(explicitIndent)"] = o[optionKeys[x]] === false ? false : true;
  5740. }
  5741. }
  5742. }
  5743. state.option = newOptionObj;
  5744. state.ignored = newIgnoredObj;
  5745. state.option.indent = state.option.indent || 4;
  5746. state.option.maxerr = state.option.maxerr || 50;
  5747. indent = 1;
  5748. global = Object.create(predefined);
  5749. scope = global;
  5750. funct = {
  5751. "(global)": true,
  5752. "(name)": "(global)",
  5753. "(scope)": scope,
  5754. "(breakage)": 0,
  5755. "(loopage)": 0,
  5756. "(tokens)": {},
  5757. "(metrics)": createMetrics(state.tokens.next),
  5758. "(blockscope)": blockScope(),
  5759. "(comparray)": arrayComprehension()
  5760. };
  5761. functions = [funct];
  5762. urls = [];
  5763. stack = null;
  5764. member = {};
  5765. membersOnly = null;
  5766. implied = {};
  5767. inblock = false;
  5768. lookahead = [];
  5769. warnings = 0;
  5770. unuseds = [];
  5771. if (!isString(s) && !Array.isArray(s)) {
  5772. errorAt("E004", 0);
  5773. return false;
  5774. }
  5775. api = {
  5776. get isJSON() {
  5777. return state.jsonMode;
  5778. },
  5779. getOption: function (name) {
  5780. return state.option[name] || null;
  5781. },
  5782. getCache: function (name) {
  5783. return state.cache[name];
  5784. },
  5785. setCache: function (name, value) {
  5786. state.cache[name] = value;
  5787. },
  5788. warn: function (code, data) {
  5789. warningAt.apply(null, [ code, data.line, data.char ].concat(data.data));
  5790. },
  5791. on: function (names, listener) {
  5792. names.split(" ").forEach(function (name) {
  5793. emitter.on(name, listener);
  5794. }.bind(this));
  5795. }
  5796. };
  5797. emitter.removeAllListeners();
  5798. (extraModules || []).forEach(function (func) {
  5799. func(api);
  5800. });
  5801. state.tokens.prev = state.tokens.curr = state.tokens.next = state.syntax["(begin)"];
  5802. lex = new Lexer(s);
  5803. lex.on("warning", function (ev) {
  5804. warningAt.apply(null, [ ev.code, ev.line, ev.character].concat(ev.data));
  5805. });
  5806. lex.on("error", function (ev) {
  5807. errorAt.apply(null, [ ev.code, ev.line, ev.character ].concat(ev.data));
  5808. });
  5809. lex.on("fatal", function (ev) {
  5810. quit("E041", ev.line, ev.from);
  5811. });
  5812. lex.on("Identifier", function (ev) {
  5813. emitter.emit("Identifier", ev);
  5814. });
  5815. lex.on("String", function (ev) {
  5816. emitter.emit("String", ev);
  5817. });
  5818. lex.on("Number", function (ev) {
  5819. emitter.emit("Number", ev);
  5820. });
  5821. lex.start();
  5822. // Check options
  5823. for (var name in o) {
  5824. if (_.has(o, name)) {
  5825. checkOption(name, state.tokens.curr);
  5826. }
  5827. }
  5828. assume();
  5829. // combine the passed globals after we've assumed all our options
  5830. combine(predefined, g || {});
  5831. //reset values
  5832. comma.first = true;
  5833. try {
  5834. advance();
  5835. switch (state.tokens.next.id) {
  5836. case "{":
  5837. case "[":
  5838. destructuringAssignOrJsonValue();
  5839. break;
  5840. default:
  5841. directives();
  5842. if (state.directive["use strict"]) {
  5843. if (!state.option.globalstrict && !state.option.node) {
  5844. warning("W097", state.tokens.prev);
  5845. }
  5846. }
  5847. statements();
  5848. }
  5849. advance((state.tokens.next && state.tokens.next.value !== ".") ? "(end)" : undefined);
  5850. funct["(blockscope)"].unstack();
  5851. var markDefined = function (name, context) {
  5852. do {
  5853. if (typeof context[name] === "string") {
  5854. // JSHINT marks unused variables as 'unused' and
  5855. // unused function declaration as 'unction'. This
  5856. // code changes such instances back 'var' and
  5857. // 'closure' so that the code in JSHINT.data()
  5858. // doesn't think they're unused.
  5859. if (context[name] === "unused")
  5860. context[name] = "var";
  5861. else if (context[name] === "unction")
  5862. context[name] = "closure";
  5863. return true;
  5864. }
  5865. context = context["(context)"];
  5866. } while (context);
  5867. return false;
  5868. };
  5869. var clearImplied = function (name, line) {
  5870. if (!implied[name])
  5871. return;
  5872. var newImplied = [];
  5873. for (var i = 0; i < implied[name].length; i += 1) {
  5874. if (implied[name][i] !== line)
  5875. newImplied.push(implied[name][i]);
  5876. }
  5877. if (newImplied.length === 0)
  5878. delete implied[name];
  5879. else
  5880. implied[name] = newImplied;
  5881. };
  5882. var warnUnused = function (name, tkn, type, unused_opt) {
  5883. var line = tkn.line;
  5884. var chr = tkn.character;
  5885. if (unused_opt === undefined) {
  5886. unused_opt = state.option.unused;
  5887. }
  5888. if (unused_opt === true) {
  5889. unused_opt = "last-param";
  5890. }
  5891. var warnable_types = {
  5892. "vars": ["var"],
  5893. "last-param": ["var", "param"],
  5894. "strict": ["var", "param", "last-param"]
  5895. };
  5896. if (unused_opt) {
  5897. if (warnable_types[unused_opt] && warnable_types[unused_opt].indexOf(type) !== -1) {
  5898. warningAt("W098", line, chr, name);
  5899. }
  5900. }
  5901. unuseds.push({
  5902. name: name,
  5903. line: line,
  5904. character: chr
  5905. });
  5906. };
  5907. var checkUnused = function (func, key) {
  5908. var type = func[key];
  5909. var tkn = func["(tokens)"][key];
  5910. if (key.charAt(0) === "(")
  5911. return;
  5912. if (type !== "unused" && type !== "unction")
  5913. return;
  5914. // Params are checked separately from other variables.
  5915. if (func["(params)"] && func["(params)"].indexOf(key) !== -1)
  5916. return;
  5917. // Variable is in global scope and defined as exported.
  5918. if (func["(global)"] && _.has(exported, key)) {
  5919. return;
  5920. }
  5921. warnUnused(key, tkn, "var");
  5922. };
  5923. // Check queued 'x is not defined' instances to see if they're still undefined.
  5924. for (i = 0; i < JSHINT.undefs.length; i += 1) {
  5925. k = JSHINT.undefs[i].slice(0);
  5926. if (markDefined(k[2].value, k[0])) {
  5927. clearImplied(k[2].value, k[2].line);
  5928. } else if (state.option.undef) {
  5929. warning.apply(warning, k.slice(1));
  5930. }
  5931. }
  5932. functions.forEach(function (func) {
  5933. if (func["(unusedOption)"] === false) {
  5934. return;
  5935. }
  5936. for (var key in func) {
  5937. if (_.has(func, key)) {
  5938. checkUnused(func, key);
  5939. }
  5940. }
  5941. if (!func["(params)"])
  5942. return;
  5943. var params = func["(params)"].slice();
  5944. var param = params.pop();
  5945. var type, unused_opt;
  5946. while (param) {
  5947. type = func[param];
  5948. unused_opt = func["(unusedOption)"] || state.option.unused;
  5949. unused_opt = unused_opt === true ? "last-param" : unused_opt;
  5950. // 'undefined' is a special case for (function (window, undefined) { ... })();
  5951. // patterns.
  5952. if (param === "undefined")
  5953. return;
  5954. if (type === "unused" || type === "unction") {
  5955. warnUnused(param, func["(tokens)"][param], "param", func["(unusedOption)"]);
  5956. } else if (unused_opt === "last-param") {
  5957. return;
  5958. }
  5959. param = params.pop();
  5960. }
  5961. });
  5962. for (var key in declared) {
  5963. if (_.has(declared, key) && !_.has(global, key)) {
  5964. warnUnused(key, declared[key], "var");
  5965. }
  5966. }
  5967. } catch (err) {
  5968. if (err && err.name === "JSHintError") {
  5969. var nt = state.tokens.next || {};
  5970. JSHINT.errors.push({
  5971. scope : "(main)",
  5972. raw : err.raw,
  5973. code : err.code,
  5974. reason : err.message,
  5975. line : err.line || nt.line,
  5976. character : err.character || nt.from
  5977. }, null);
  5978. } else {
  5979. throw err;
  5980. }
  5981. }
  5982. // Loop over the listed "internals", and check them as well.
  5983. if (JSHINT.scope === "(main)") {
  5984. o = o || {};
  5985. for (i = 0; i < JSHINT.internals.length; i += 1) {
  5986. k = JSHINT.internals[i];
  5987. o.scope = k.elem;
  5988. itself(k.value, o, g);
  5989. }
  5990. }
  5991. return JSHINT.errors.length === 0;
  5992. };
  5993. // Modules.
  5994. itself.addModule = function (func) {
  5995. extraModules.push(func);
  5996. };
  5997. itself.addModule(style.register);
  5998. // Data summary.
  5999. itself.data = function () {
  6000. var data = {
  6001. functions: [],
  6002. options: state.option
  6003. };
  6004. var implieds = [];
  6005. var members = [];
  6006. var fu, f, i, j, n, globals;
  6007. if (itself.errors.length) {
  6008. data.errors = itself.errors;
  6009. }
  6010. if (state.jsonMode) {
  6011. data.json = true;
  6012. }
  6013. for (n in implied) {
  6014. if (_.has(implied, n)) {
  6015. implieds.push({
  6016. name: n,
  6017. line: implied[n]
  6018. });
  6019. }
  6020. }
  6021. if (implieds.length > 0) {
  6022. data.implieds = implieds;
  6023. }
  6024. if (urls.length > 0) {
  6025. data.urls = urls;
  6026. }
  6027. globals = Object.keys(scope);
  6028. if (globals.length > 0) {
  6029. data.globals = globals;
  6030. }
  6031. for (i = 1; i < functions.length; i += 1) {
  6032. f = functions[i];
  6033. fu = {};
  6034. for (j = 0; j < functionicity.length; j += 1) {
  6035. fu[functionicity[j]] = [];
  6036. }
  6037. for (j = 0; j < functionicity.length; j += 1) {
  6038. if (fu[functionicity[j]].length === 0) {
  6039. delete fu[functionicity[j]];
  6040. }
  6041. }
  6042. fu.name = f["(name)"];
  6043. fu.param = f["(params)"];
  6044. fu.line = f["(line)"];
  6045. fu.character = f["(character)"];
  6046. fu.last = f["(last)"];
  6047. fu.lastcharacter = f["(lastcharacter)"];
  6048. data.functions.push(fu);
  6049. }
  6050. if (unuseds.length > 0) {
  6051. data.unused = unuseds;
  6052. }
  6053. members = [];
  6054. for (n in member) {
  6055. if (typeof member[n] === "number") {
  6056. data.member = member;
  6057. break;
  6058. }
  6059. }
  6060. return data;
  6061. };
  6062. itself.jshint = itself;
  6063. return itself;
  6064. }());
  6065. // Make JSHINT a Node module, if possible.
  6066. if (typeof exports === "object" && exports) {
  6067. exports.JSHINT = JSHINT;
  6068. }
  6069. },
  6070. {"../shared/messages.js":2,"../shared/vars.js":3,"./lex.js":5,"./reg.js":6,"./state.js":7,"./style.js":8,"console-browserify":9,"events":10,"underscore":1}],
  6071. 5:[function(req,module,exports){
  6072. /*
  6073. * Lexical analysis and token construction.
  6074. */
  6075. "use strict";
  6076. var _ = req("underscore");
  6077. var events = req("events");
  6078. var reg = req("./reg.js");
  6079. var state = req("./state.js").state;
  6080. // Some of these token types are from JavaScript Parser API
  6081. // while others are specific to JSHint parser.
  6082. // JS Parser API: https://developer.mozilla.org/en-US/docs/SpiderMonkey/Parser_API
  6083. var Token = {
  6084. Identifier: 1,
  6085. Punctuator: 2,
  6086. NumericLiteral: 3,
  6087. StringLiteral: 4,
  6088. Comment: 5,
  6089. Keyword: 6,
  6090. NullLiteral: 7,
  6091. BooleanLiteral: 8,
  6092. RegExp: 9
  6093. };
  6094. // This is auto generated from the unicode tables.
  6095. // The tables are at:
  6096. // http://www.fileformat.info/info/unicode/category/Lu/list.htm
  6097. // http://www.fileformat.info/info/unicode/category/Ll/list.htm
  6098. // http://www.fileformat.info/info/unicode/category/Lt/list.htm
  6099. // http://www.fileformat.info/info/unicode/category/Lm/list.htm
  6100. // http://www.fileformat.info/info/unicode/category/Lo/list.htm
  6101. // http://www.fileformat.info/info/unicode/category/Nl/list.htm
  6102. var unicodeLetterTable = [
  6103. 170, 170, 181, 181, 186, 186, 192, 214,
  6104. 216, 246, 248, 705, 710, 721, 736, 740, 748, 748, 750, 750,
  6105. 880, 884, 886, 887, 890, 893, 902, 902, 904, 906, 908, 908,
  6106. 910, 929, 931, 1013, 1015, 1153, 1162, 1319, 1329, 1366,
  6107. 1369, 1369, 1377, 1415, 1488, 1514, 1520, 1522, 1568, 1610,
  6108. 1646, 1647, 1649, 1747, 1749, 1749, 1765, 1766, 1774, 1775,
  6109. 1786, 1788, 1791, 1791, 1808, 1808, 1810, 1839, 1869, 1957,
  6110. 1969, 1969, 1994, 2026, 2036, 2037, 2042, 2042, 2048, 2069,
  6111. 2074, 2074, 2084, 2084, 2088, 2088, 2112, 2136, 2308, 2361,
  6112. 2365, 2365, 2384, 2384, 2392, 2401, 2417, 2423, 2425, 2431,
  6113. 2437, 2444, 2447, 2448, 2451, 2472, 2474, 2480, 2482, 2482,
  6114. 2486, 2489, 2493, 2493, 2510, 2510, 2524, 2525, 2527, 2529,
  6115. 2544, 2545, 2565, 2570, 2575, 2576, 2579, 2600, 2602, 2608,
  6116. 2610, 2611, 2613, 2614, 2616, 2617, 2649, 2652, 2654, 2654,
  6117. 2674, 2676, 2693, 2701, 2703, 2705, 2707, 2728, 2730, 2736,
  6118. 2738, 2739, 2741, 2745, 2749, 2749, 2768, 2768, 2784, 2785,
  6119. 2821, 2828, 2831, 2832, 2835, 2856, 2858, 2864, 2866, 2867,
  6120. 2869, 2873, 2877, 2877, 2908, 2909, 2911, 2913, 2929, 2929,
  6121. 2947, 2947, 2949, 2954, 2958, 2960, 2962, 2965, 2969, 2970,
  6122. 2972, 2972, 2974, 2975, 2979, 2980, 2984, 2986, 2990, 3001,
  6123. 3024, 3024, 3077, 3084, 3086, 3088, 3090, 3112, 3114, 3123,
  6124. 3125, 3129, 3133, 3133, 3160, 3161, 3168, 3169, 3205, 3212,
  6125. 3214, 3216, 3218, 3240, 3242, 3251, 3253, 3257, 3261, 3261,
  6126. 3294, 3294, 3296, 3297, 3313, 3314, 3333, 3340, 3342, 3344,
  6127. 3346, 3386, 3389, 3389, 3406, 3406, 3424, 3425, 3450, 3455,
  6128. 3461, 3478, 3482, 3505, 3507, 3515, 3517, 3517, 3520, 3526,
  6129. 3585, 3632, 3634, 3635, 3648, 3654, 3713, 3714, 3716, 3716,
  6130. 3719, 3720, 3722, 3722, 3725, 3725, 3732, 3735, 3737, 3743,
  6131. 3745, 3747, 3749, 3749, 3751, 3751, 3754, 3755, 3757, 3760,
  6132. 3762, 3763, 3773, 3773, 3776, 3780, 3782, 3782, 3804, 3805,
  6133. 3840, 3840, 3904, 3911, 3913, 3948, 3976, 3980, 4096, 4138,
  6134. 4159, 4159, 4176, 4181, 4186, 4189, 4193, 4193, 4197, 4198,
  6135. 4206, 4208, 4213, 4225, 4238, 4238, 4256, 4293, 4304, 4346,
  6136. 4348, 4348, 4352, 4680, 4682, 4685, 4688, 4694, 4696, 4696,
  6137. 4698, 4701, 4704, 4744, 4746, 4749, 4752, 4784, 4786, 4789,
  6138. 4792, 4798, 4800, 4800, 4802, 4805, 4808, 4822, 4824, 4880,
  6139. 4882, 4885, 4888, 4954, 4992, 5007, 5024, 5108, 5121, 5740,
  6140. 5743, 5759, 5761, 5786, 5792, 5866, 5870, 5872, 5888, 5900,
  6141. 5902, 5905, 5920, 5937, 5952, 5969, 5984, 5996, 5998, 6000,
  6142. 6016, 6067, 6103, 6103, 6108, 6108, 6176, 6263, 6272, 6312,
  6143. 6314, 6314, 6320, 6389, 6400, 6428, 6480, 6509, 6512, 6516,
  6144. 6528, 6571, 6593, 6599, 6656, 6678, 6688, 6740, 6823, 6823,
  6145. 6917, 6963, 6981, 6987, 7043, 7072, 7086, 7087, 7104, 7141,
  6146. 7168, 7203, 7245, 7247, 7258, 7293, 7401, 7404, 7406, 7409,
  6147. 7424, 7615, 7680, 7957, 7960, 7965, 7968, 8005, 8008, 8013,
  6148. 8016, 8023, 8025, 8025, 8027, 8027, 8029, 8029, 8031, 8061,
  6149. 8064, 8116, 8118, 8124, 8126, 8126, 8130, 8132, 8134, 8140,
  6150. 8144, 8147, 8150, 8155, 8160, 8172, 8178, 8180, 8182, 8188,
  6151. 8305, 8305, 8319, 8319, 8336, 8348, 8450, 8450, 8455, 8455,
  6152. 8458, 8467, 8469, 8469, 8473, 8477, 8484, 8484, 8486, 8486,
  6153. 8488, 8488, 8490, 8493, 8495, 8505, 8508, 8511, 8517, 8521,
  6154. 8526, 8526, 8544, 8584, 11264, 11310, 11312, 11358,
  6155. 11360, 11492, 11499, 11502, 11520, 11557, 11568, 11621,
  6156. 11631, 11631, 11648, 11670, 11680, 11686, 11688, 11694,
  6157. 11696, 11702, 11704, 11710, 11712, 11718, 11720, 11726,
  6158. 11728, 11734, 11736, 11742, 11823, 11823, 12293, 12295,
  6159. 12321, 12329, 12337, 12341, 12344, 12348, 12353, 12438,
  6160. 12445, 12447, 12449, 12538, 12540, 12543, 12549, 12589,
  6161. 12593, 12686, 12704, 12730, 12784, 12799, 13312, 13312,
  6162. 19893, 19893, 19968, 19968, 40907, 40907, 40960, 42124,
  6163. 42192, 42237, 42240, 42508, 42512, 42527, 42538, 42539,
  6164. 42560, 42606, 42623, 42647, 42656, 42735, 42775, 42783,
  6165. 42786, 42888, 42891, 42894, 42896, 42897, 42912, 42921,
  6166. 43002, 43009, 43011, 43013, 43015, 43018, 43020, 43042,
  6167. 43072, 43123, 43138, 43187, 43250, 43255, 43259, 43259,
  6168. 43274, 43301, 43312, 43334, 43360, 43388, 43396, 43442,
  6169. 43471, 43471, 43520, 43560, 43584, 43586, 43588, 43595,
  6170. 43616, 43638, 43642, 43642, 43648, 43695, 43697, 43697,
  6171. 43701, 43702, 43705, 43709, 43712, 43712, 43714, 43714,
  6172. 43739, 43741, 43777, 43782, 43785, 43790, 43793, 43798,
  6173. 43808, 43814, 43816, 43822, 43968, 44002, 44032, 44032,
  6174. 55203, 55203, 55216, 55238, 55243, 55291, 63744, 64045,
  6175. 64048, 64109, 64112, 64217, 64256, 64262, 64275, 64279,
  6176. 64285, 64285, 64287, 64296, 64298, 64310, 64312, 64316,
  6177. 64318, 64318, 64320, 64321, 64323, 64324, 64326, 64433,
  6178. 64467, 64829, 64848, 64911, 64914, 64967, 65008, 65019,
  6179. 65136, 65140, 65142, 65276, 65313, 65338, 65345, 65370,
  6180. 65382, 65470, 65474, 65479, 65482, 65487, 65490, 65495,
  6181. 65498, 65500, 65536, 65547, 65549, 65574, 65576, 65594,
  6182. 65596, 65597, 65599, 65613, 65616, 65629, 65664, 65786,
  6183. 65856, 65908, 66176, 66204, 66208, 66256, 66304, 66334,
  6184. 66352, 66378, 66432, 66461, 66464, 66499, 66504, 66511,
  6185. 66513, 66517, 66560, 66717, 67584, 67589, 67592, 67592,
  6186. 67594, 67637, 67639, 67640, 67644, 67644, 67647, 67669,
  6187. 67840, 67861, 67872, 67897, 68096, 68096, 68112, 68115,
  6188. 68117, 68119, 68121, 68147, 68192, 68220, 68352, 68405,
  6189. 68416, 68437, 68448, 68466, 68608, 68680, 69635, 69687,
  6190. 69763, 69807, 73728, 74606, 74752, 74850, 77824, 78894,
  6191. 92160, 92728, 110592, 110593, 119808, 119892, 119894, 119964,
  6192. 119966, 119967, 119970, 119970, 119973, 119974, 119977, 119980,
  6193. 119982, 119993, 119995, 119995, 119997, 120003, 120005, 120069,
  6194. 120071, 120074, 120077, 120084, 120086, 120092, 120094, 120121,
  6195. 120123, 120126, 120128, 120132, 120134, 120134, 120138, 120144,
  6196. 120146, 120485, 120488, 120512, 120514, 120538, 120540, 120570,
  6197. 120572, 120596, 120598, 120628, 120630, 120654, 120656, 120686,
  6198. 120688, 120712, 120714, 120744, 120746, 120770, 120772, 120779,
  6199. 131072, 131072, 173782, 173782, 173824, 173824, 177972, 177972,
  6200. 177984, 177984, 178205, 178205, 194560, 195101
  6201. ];
  6202. var identifierStartTable = [];
  6203. for (var i = 0; i < 128; i++) {
  6204. identifierStartTable[i] =
  6205. i === 36 || // $
  6206. i >= 65 && i <= 90 || // A-Z
  6207. i === 95 || // _
  6208. i >= 97 && i <= 122; // a-z
  6209. }
  6210. var identifierPartTable = [];
  6211. for (var i = 0; i < 128; i++) {
  6212. identifierPartTable[i] =
  6213. identifierStartTable[i] || // $, _, A-Z, a-z
  6214. i >= 48 && i <= 57; // 0-9
  6215. }
  6216. // Object that handles postponed lexing verifications that checks the parsed
  6217. // environment state.
  6218. function asyncTrigger() {
  6219. var _checks = [];
  6220. return {
  6221. push: function (fn) {
  6222. _checks.push(fn);
  6223. },
  6224. check: function () {
  6225. for (var check = 0; check < _checks.length; ++check) {
  6226. _checks[check]();
  6227. }
  6228. _checks.splice(0, _checks.length);
  6229. }
  6230. };
  6231. }
  6232. /*
  6233. * Lexer for JSHint.
  6234. *
  6235. * This object does a char-by-char scan of the provided source code
  6236. * and produces a sequence of tokens.
  6237. *
  6238. * var lex = new Lexer("var i = 0;");
  6239. * lex.start();
  6240. * lex.token(); // returns the next token
  6241. *
  6242. * You have to use the token() method to move the lexer forward
  6243. * but you don't have to use its return value to get tokens. In addition
  6244. * to token() method returning the next token, the Lexer object also
  6245. * emits events.
  6246. *
  6247. * lex.on("Identifier", function (data) {
  6248. * if (data.name.indexOf("_") >= 0) {
  6249. * // Produce a warning.
  6250. * }
  6251. * });
  6252. *
  6253. * Note that the token() method returns tokens in a JSLint-compatible
  6254. * format while the event emitter uses a slightly modified version of
  6255. * Mozilla's JavaScript Parser API. Eventually, we will move away from
  6256. * JSLint format.
  6257. */
  6258. function Lexer(source) {
  6259. var lines = source;
  6260. if (typeof lines === "string") {
  6261. lines = lines
  6262. .replace(/\r\n/g, "\n")
  6263. .replace(/\r/g, "\n")
  6264. .split("\n");
  6265. }
  6266. // If the first line is a shebang (#!), make it a blank and move on.
  6267. // Shebangs are used by Node scripts.
  6268. if (lines[0] && lines[0].substr(0, 2) === "#!") {
  6269. lines[0] = "";
  6270. }
  6271. this.emitter = new events.EventEmitter();
  6272. this.source = source;
  6273. this.setLines(lines);
  6274. this.prereg = true;
  6275. this.line = 0;
  6276. this.char = 1;
  6277. this.from = 1;
  6278. this.input = "";
  6279. for (var i = 0; i < state.option.indent; i += 1) {
  6280. state.tab += " ";
  6281. }
  6282. }
  6283. Lexer.prototype = {
  6284. _lines: [],
  6285. getLines: function () {
  6286. this._lines = state.lines;
  6287. return this._lines;
  6288. },
  6289. setLines: function (val) {
  6290. this._lines = val;
  6291. state.lines = this._lines;
  6292. },
  6293. /*
  6294. * Return the next i character without actually moving the
  6295. * char pointer.
  6296. */
  6297. peek: function (i) {
  6298. return this.input.charAt(i || 0);
  6299. },
  6300. /*
  6301. * Move the char pointer forward i times.
  6302. */
  6303. skip: function (i) {
  6304. i = i || 1;
  6305. this.char += i;
  6306. this.input = this.input.slice(i);
  6307. },
  6308. /*
  6309. * Subscribe to a token event. The API for this method is similar
  6310. * Underscore.js i.e. you can subscribe to multiple events with
  6311. * one call:
  6312. *
  6313. * lex.on("Identifier Number", function (data) {
  6314. * // ...
  6315. * });
  6316. */
  6317. on: function (names, listener) {
  6318. names.split(" ").forEach(function (name) {
  6319. this.emitter.on(name, listener);
  6320. }.bind(this));
  6321. },
  6322. /*
  6323. * Trigger a token event. All arguments will be passed to each
  6324. * listener.
  6325. */
  6326. trigger: function () {
  6327. this.emitter.emit.apply(this.emitter, Array.prototype.slice.call(arguments));
  6328. },
  6329. /*
  6330. * Postpone a token event. the checking condition is set as
  6331. * last parameter, and the trigger function is called in a
  6332. * stored callback. To be later called using the check() function
  6333. * by the parser. This avoids parser's peek() to give the lexer
  6334. * a false context.
  6335. */
  6336. triggerAsync: function (type, args, checks, fn) {
  6337. checks.push(function () {
  6338. if (fn()) {
  6339. this.trigger(type, args);
  6340. }
  6341. }.bind(this));
  6342. },
  6343. /*
  6344. * Extract a punctuator out of the next sequence of characters
  6345. * or return 'null' if its not possible.
  6346. *
  6347. * This method's implementation was heavily influenced by the
  6348. * scanPunctuator function in the Esprima parser's source code.
  6349. */
  6350. scanPunctuator: function () {
  6351. var ch1 = this.peek();
  6352. var ch2, ch3, ch4;
  6353. switch (ch1) {
  6354. // Most common single-character punctuators
  6355. case ".":
  6356. if ((/^[0-9]$/).test(this.peek(1))) {
  6357. return null;
  6358. }
  6359. if (this.peek(1) === "." && this.peek(2) === ".") {
  6360. return {
  6361. type: Token.Punctuator,
  6362. value: "..."
  6363. };
  6364. }
  6365. /* falls through */
  6366. case "(":
  6367. case ")":
  6368. case ";":
  6369. case ",":
  6370. case "{":
  6371. case "}":
  6372. case "[":
  6373. case "]":
  6374. case ":":
  6375. case "~":
  6376. case "?":
  6377. return {
  6378. type: Token.Punctuator,
  6379. value: ch1
  6380. };
  6381. // A pound sign (for Node shebangs)
  6382. case "#":
  6383. return {
  6384. type: Token.Punctuator,
  6385. value: ch1
  6386. };
  6387. // We're at the end of input
  6388. case "":
  6389. return null;
  6390. }
  6391. // Peek more characters
  6392. ch2 = this.peek(1);
  6393. ch3 = this.peek(2);
  6394. ch4 = this.peek(3);
  6395. // 4-character punctuator: >>>=
  6396. if (ch1 === ">" && ch2 === ">" && ch3 === ">" && ch4 === "=") {
  6397. return {
  6398. type: Token.Punctuator,
  6399. value: ">>>="
  6400. };
  6401. }
  6402. // 3-character punctuators: === !== >>> <<= >>=
  6403. if (ch1 === "=" && ch2 === "=" && ch3 === "=") {
  6404. return {
  6405. type: Token.Punctuator,
  6406. value: "==="
  6407. };
  6408. }
  6409. if (ch1 === "!" && ch2 === "=" && ch3 === "=") {
  6410. return {
  6411. type: Token.Punctuator,
  6412. value: "!=="
  6413. };
  6414. }
  6415. if (ch1 === ">" && ch2 === ">" && ch3 === ">") {
  6416. return {
  6417. type: Token.Punctuator,
  6418. value: ">>>"
  6419. };
  6420. }
  6421. if (ch1 === "<" && ch2 === "<" && ch3 === "=") {
  6422. return {
  6423. type: Token.Punctuator,
  6424. value: "<<="
  6425. };
  6426. }
  6427. if (ch1 === ">" && ch2 === ">" && ch3 === "=") {
  6428. return {
  6429. type: Token.Punctuator,
  6430. value: ">>="
  6431. };
  6432. }
  6433. // Fat arrow punctuator
  6434. if (ch1 === "=" && ch2 === ">") {
  6435. return {
  6436. type: Token.Punctuator,
  6437. value: ch1 + ch2
  6438. };
  6439. }
  6440. // 2-character punctuators: <= >= == != ++ -- << >> && ||
  6441. // += -= *= %= &= |= ^= (but not /=, see below)
  6442. if (ch1 === ch2 && ("+-<>&|".indexOf(ch1) >= 0)) {
  6443. return {
  6444. type: Token.Punctuator,
  6445. value: ch1 + ch2
  6446. };
  6447. }
  6448. if ("<>=!+-*%&|^".indexOf(ch1) >= 0) {
  6449. if (ch2 === "=") {
  6450. return {
  6451. type: Token.Punctuator,
  6452. value: ch1 + ch2
  6453. };
  6454. }
  6455. return {
  6456. type: Token.Punctuator,
  6457. value: ch1
  6458. };
  6459. }
  6460. // Special case: /=. We need to make sure that this is an
  6461. // operator and not a regular expression.
  6462. if (ch1 === "/") {
  6463. if (ch2 === "=" && /\/=(?!(\S*\/[gim]?))/.test(this.input)) {
  6464. // /= is not a part of a regular expression, return it as a
  6465. // punctuator.
  6466. return {
  6467. type: Token.Punctuator,
  6468. value: "/="
  6469. };
  6470. }
  6471. return {
  6472. type: Token.Punctuator,
  6473. value: "/"
  6474. };
  6475. }
  6476. return null;
  6477. },
  6478. /*
  6479. * Extract a comment out of the next sequence of characters and/or
  6480. * lines or return 'null' if its not possible. Since comments can
  6481. * span across multiple lines this method has to move the char
  6482. * pointer.
  6483. *
  6484. * In addition to normal JavaScript comments (// and /*) this method
  6485. * also recognizes JSHint- and JSLint-specific comments such as
  6486. * /*jshint, /*jslint, /*globals and so on.
  6487. */
  6488. scanComments: function () {
  6489. var ch1 = this.peek();
  6490. var ch2 = this.peek(1);
  6491. var rest = this.input.substr(2);
  6492. var startLine = this.line;
  6493. var startChar = this.char;
  6494. // Create a comment token object and make sure it
  6495. // has all the data JSHint needs to work with special
  6496. // comments.
  6497. function commentToken(label, body, opt) {
  6498. var special = ["jshint", "jslint", "members", "member", "globals", "global", "exported"];
  6499. var isSpecial = false;
  6500. var value = label + body;
  6501. var commentType = "plain";
  6502. opt = opt || {};
  6503. if (opt.isMultiline) {
  6504. value += "*/";
  6505. }
  6506. special.forEach(function (str) {
  6507. if (isSpecial) {
  6508. return;
  6509. }
  6510. // Don't recognize any special comments other than jshint for single-line
  6511. // comments. This introduced many problems with legit comments.
  6512. if (label === "//" && str !== "jshint") {
  6513. return;
  6514. }
  6515. if (body.substr(0, str.length) === str) {
  6516. isSpecial = true;
  6517. label = label + str;
  6518. body = body.substr(str.length);
  6519. }
  6520. if (!isSpecial && body.charAt(0) === " " && body.substr(1, str.length) === str) {
  6521. isSpecial = true;
  6522. label = label + " " + str;
  6523. body = body.substr(str.length + 1);
  6524. }
  6525. if (!isSpecial) {
  6526. return;
  6527. }
  6528. switch (str) {
  6529. case "member":
  6530. commentType = "members";
  6531. break;
  6532. case "global":
  6533. commentType = "globals";
  6534. break;
  6535. default:
  6536. commentType = str;
  6537. }
  6538. });
  6539. return {
  6540. type: Token.Comment,
  6541. commentType: commentType,
  6542. value: value,
  6543. body: body,
  6544. isSpecial: isSpecial,
  6545. isMultiline: opt.isMultiline || false,
  6546. isMalformed: opt.isMalformed || false
  6547. };
  6548. }
  6549. // End of unbegun comment. Raise an error and skip that input.
  6550. if (ch1 === "*" && ch2 === "/") {
  6551. this.trigger("error", {
  6552. code: "E018",
  6553. line: startLine,
  6554. character: startChar
  6555. });
  6556. this.skip(2);
  6557. return null;
  6558. }
  6559. // Comments must start either with // or /*
  6560. if (ch1 !== "/" || (ch2 !== "*" && ch2 !== "/")) {
  6561. return null;
  6562. }
  6563. // One-line comment
  6564. if (ch2 === "/") {
  6565. this.skip(this.input.length); // Skip to the EOL.
  6566. return commentToken("//", rest);
  6567. }
  6568. var body = "";
  6569. /* Multi-line comment */
  6570. if (ch2 === "*") {
  6571. this.skip(2);
  6572. while (this.peek() !== "*" || this.peek(1) !== "/") {
  6573. if (this.peek() === "") { // End of Line
  6574. body += "\n";
  6575. // If we hit EOF and our comment is still unclosed,
  6576. // trigger an error and end the comment implicitly.
  6577. if (!this.nextLine()) {
  6578. this.trigger("error", {
  6579. code: "E017",
  6580. line: startLine,
  6581. character: startChar
  6582. });
  6583. return commentToken("/*", body, {
  6584. isMultiline: true,
  6585. isMalformed: true
  6586. });
  6587. }
  6588. } else {
  6589. body += this.peek();
  6590. this.skip();
  6591. }
  6592. }
  6593. this.skip(2);
  6594. return commentToken("/*", body, { isMultiline: true });
  6595. }
  6596. },
  6597. /*
  6598. * Extract a keyword out of the next sequence of characters or
  6599. * return 'null' if its not possible.
  6600. */
  6601. scanKeyword: function () {
  6602. var result = /^[a-zA-Z_$][a-zA-Z0-9_$]*/.exec(this.input);
  6603. var keywords = [
  6604. "if", "in", "do", "var", "for", "new",
  6605. "try", "let", "this", "else", "case",
  6606. "void", "with", "enum", "while", "break",
  6607. "catch", "throw", "const", "yield", "class",
  6608. "super", "return", "typeof", "delete",
  6609. "switch", "export", "import", "default",
  6610. "finally", "extends", "function", "continue",
  6611. "debugger", "instanceof"
  6612. ];
  6613. if (result && keywords.indexOf(result[0]) >= 0) {
  6614. return {
  6615. type: Token.Keyword,
  6616. value: result[0]
  6617. };
  6618. }
  6619. return null;
  6620. },
  6621. /*
  6622. * Extract a JavaScript identifier out of the next sequence of
  6623. * characters or return 'null' if its not possible. In addition,
  6624. * to Identifier this method can also produce BooleanLiteral
  6625. * (true/false) and NullLiteral (null).
  6626. */
  6627. scanIdentifier: function () {
  6628. var id = "";
  6629. var index = 0;
  6630. var type, char;
  6631. // Detects any character in the Unicode categories "Uppercase
  6632. // letter (Lu)", "Lowercase letter (Ll)", "Titlecase letter
  6633. // (Lt)", "Modifier letter (Lm)", "Other letter (Lo)", or
  6634. // "Letter number (Nl)".
  6635. //
  6636. // Both approach and unicodeLetterTable were borrowed from
  6637. // Google's Traceur.
  6638. function isUnicodeLetter(code) {
  6639. for (var i = 0; i < unicodeLetterTable.length;) {
  6640. if (code < unicodeLetterTable[i++]) {
  6641. return false;
  6642. }
  6643. if (code <= unicodeLetterTable[i++]) {
  6644. return true;
  6645. }
  6646. }
  6647. return false;
  6648. }
  6649. function isHexDigit(str) {
  6650. return (/^[0-9a-fA-F]$/).test(str);
  6651. }
  6652. var readUnicodeEscapeSequence = function () {
  6653. /*jshint validthis:true */
  6654. index += 1;
  6655. if (this.peek(index) !== "u") {
  6656. return null;
  6657. }
  6658. var ch1 = this.peek(index + 1);
  6659. var ch2 = this.peek(index + 2);
  6660. var ch3 = this.peek(index + 3);
  6661. var ch4 = this.peek(index + 4);
  6662. var code;
  6663. if (isHexDigit(ch1) && isHexDigit(ch2) && isHexDigit(ch3) && isHexDigit(ch4)) {
  6664. code = parseInt(ch1 + ch2 + ch3 + ch4, 16);
  6665. if (isUnicodeLetter(code)) {
  6666. index += 5;
  6667. return "\\u" + ch1 + ch2 + ch3 + ch4;
  6668. }
  6669. return null;
  6670. }
  6671. return null;
  6672. }.bind(this);
  6673. var getIdentifierStart = function () {
  6674. /*jshint validthis:true */
  6675. var chr = this.peek(index);
  6676. var code = chr.charCodeAt(0);
  6677. if (code === 92) {
  6678. return readUnicodeEscapeSequence();
  6679. }
  6680. if (code < 128) {
  6681. if (identifierStartTable[code]) {
  6682. index += 1;
  6683. return chr;
  6684. }
  6685. return null;
  6686. }
  6687. if (isUnicodeLetter(code)) {
  6688. index += 1;
  6689. return chr;
  6690. }
  6691. return null;
  6692. }.bind(this);
  6693. var getIdentifierPart = function () {
  6694. /*jshint validthis:true */
  6695. var chr = this.peek(index);
  6696. var code = chr.charCodeAt(0);
  6697. if (code === 92) {
  6698. return readUnicodeEscapeSequence();
  6699. }
  6700. if (code < 128) {
  6701. if (identifierPartTable[code]) {
  6702. index += 1;
  6703. return chr;
  6704. }
  6705. return null;
  6706. }
  6707. if (isUnicodeLetter(code)) {
  6708. index += 1;
  6709. return chr;
  6710. }
  6711. return null;
  6712. }.bind(this);
  6713. char = getIdentifierStart();
  6714. if (char === null) {
  6715. return null;
  6716. }
  6717. id = char;
  6718. for (;;) {
  6719. char = getIdentifierPart();
  6720. if (char === null) {
  6721. break;
  6722. }
  6723. id += char;
  6724. }
  6725. switch (id) {
  6726. case "true":
  6727. case "false":
  6728. type = Token.BooleanLiteral;
  6729. break;
  6730. case "null":
  6731. type = Token.NullLiteral;
  6732. break;
  6733. default:
  6734. type = Token.Identifier;
  6735. }
  6736. return {
  6737. type: type,
  6738. value: id
  6739. };
  6740. },
  6741. /*
  6742. * Extract a numeric literal out of the next sequence of
  6743. * characters or return 'null' if its not possible. This method
  6744. * supports all numeric literals described in section 7.8.3
  6745. * of the EcmaScript 5 specification.
  6746. *
  6747. * This method's implementation was heavily influenced by the
  6748. * scanNumericLiteral function in the Esprima parser's source code.
  6749. */
  6750. scanNumericLiteral: function () {
  6751. var index = 0;
  6752. var value = "";
  6753. var length = this.input.length;
  6754. var char = this.peek(index);
  6755. var bad;
  6756. function isDecimalDigit(str) {
  6757. return (/^[0-9]$/).test(str);
  6758. }
  6759. function isOctalDigit(str) {
  6760. return (/^[0-7]$/).test(str);
  6761. }
  6762. function isHexDigit(str) {
  6763. return (/^[0-9a-fA-F]$/).test(str);
  6764. }
  6765. function isIdentifierStart(ch) {
  6766. return (ch === "$") || (ch === "_") || (ch === "\\") ||
  6767. (ch >= "a" && ch <= "z") || (ch >= "A" && ch <= "Z");
  6768. }
  6769. // Numbers must start either with a decimal digit or a point.
  6770. if (char !== "." && !isDecimalDigit(char)) {
  6771. return null;
  6772. }
  6773. if (char !== ".") {
  6774. value = this.peek(index);
  6775. index += 1;
  6776. char = this.peek(index);
  6777. if (value === "0") {
  6778. // Base-16 numbers.
  6779. if (char === "x" || char === "X") {
  6780. index += 1;
  6781. value += char;
  6782. while (index < length) {
  6783. char = this.peek(index);
  6784. if (!isHexDigit(char)) {
  6785. break;
  6786. }
  6787. value += char;
  6788. index += 1;
  6789. }
  6790. if (value.length <= 2) { // 0x
  6791. return {
  6792. type: Token.NumericLiteral,
  6793. value: value,
  6794. isMalformed: true
  6795. };
  6796. }
  6797. if (index < length) {
  6798. char = this.peek(index);
  6799. if (isIdentifierStart(char)) {
  6800. return null;
  6801. }
  6802. }
  6803. return {
  6804. type: Token.NumericLiteral,
  6805. value: value,
  6806. base: 16,
  6807. isMalformed: false
  6808. };
  6809. }
  6810. // Base-8 numbers.
  6811. if (isOctalDigit(char)) {
  6812. index += 1;
  6813. value += char;
  6814. bad = false;
  6815. while (index < length) {
  6816. char = this.peek(index);
  6817. // Numbers like '019' (note the 9) are not valid octals
  6818. // but we still parse them and mark as malformed.
  6819. if (isDecimalDigit(char)) {
  6820. bad = true;
  6821. } else if (!isOctalDigit(char)) {
  6822. break;
  6823. }
  6824. value += char;
  6825. index += 1;
  6826. }
  6827. if (index < length) {
  6828. char = this.peek(index);
  6829. if (isIdentifierStart(char)) {
  6830. return null;
  6831. }
  6832. }
  6833. return {
  6834. type: Token.NumericLiteral,
  6835. value: value,
  6836. base: 8,
  6837. isMalformed: false
  6838. };
  6839. }
  6840. // Decimal numbers that start with '0' such as '09' are illegal
  6841. // but we still parse them and return as malformed.
  6842. if (isDecimalDigit(char)) {
  6843. index += 1;
  6844. value += char;
  6845. }
  6846. }
  6847. while (index < length) {
  6848. char = this.peek(index);
  6849. if (!isDecimalDigit(char)) {
  6850. break;
  6851. }
  6852. value += char;
  6853. index += 1;
  6854. }
  6855. }
  6856. // Decimal digits.
  6857. if (char === ".") {
  6858. value += char;
  6859. index += 1;
  6860. while (index < length) {
  6861. char = this.peek(index);
  6862. if (!isDecimalDigit(char)) {
  6863. break;
  6864. }
  6865. value += char;
  6866. index += 1;
  6867. }
  6868. }
  6869. // Exponent part.
  6870. if (char === "e" || char === "E") {
  6871. value += char;
  6872. index += 1;
  6873. char = this.peek(index);
  6874. if (char === "+" || char === "-") {
  6875. value += this.peek(index);
  6876. index += 1;
  6877. }
  6878. char = this.peek(index);
  6879. if (isDecimalDigit(char)) {
  6880. value += char;
  6881. index += 1;
  6882. while (index < length) {
  6883. char = this.peek(index);
  6884. if (!isDecimalDigit(char)) {
  6885. break;
  6886. }
  6887. value += char;
  6888. index += 1;
  6889. }
  6890. } else {
  6891. return null;
  6892. }
  6893. }
  6894. if (index < length) {
  6895. char = this.peek(index);
  6896. if (isIdentifierStart(char)) {
  6897. return null;
  6898. }
  6899. }
  6900. return {
  6901. type: Token.NumericLiteral,
  6902. value: value,
  6903. base: 10,
  6904. isMalformed: !isFinite(value)
  6905. };
  6906. },
  6907. /*
  6908. * Extract a string out of the next sequence of characters and/or
  6909. * lines or return 'null' if its not possible. Since strings can
  6910. * span across multiple lines this method has to move the char
  6911. * pointer.
  6912. *
  6913. * This method recognizes pseudo-multiline JavaScript strings:
  6914. *
  6915. * var str = "hello\
  6916. * world";
  6917. */
  6918. scanStringLiteral: function (checks) {
  6919. /*jshint loopfunc:true */
  6920. var quote = this.peek();
  6921. // String must start with a quote.
  6922. if (quote !== "\"" && quote !== "'") {
  6923. return null;
  6924. }
  6925. // In JSON strings must always use double quotes.
  6926. this.triggerAsync("warning", {
  6927. code: "W108",
  6928. line: this.line,
  6929. character: this.char // +1?
  6930. }, checks, function () { return state.jsonMode && quote !== "\""; });
  6931. var value = "";
  6932. var startLine = this.line;
  6933. var startChar = this.char;
  6934. var allowNewLine = false;
  6935. this.skip();
  6936. outer: while (this.peek() !== quote) {
  6937. while (this.peek() === "") { // End Of Line
  6938. // If an EOL is not preceded by a backslash, show a warning
  6939. // and proceed like it was a legit multi-line string where
  6940. // author simply forgot to escape the newline symbol.
  6941. //
  6942. // Another approach is to implicitly close a string on EOL
  6943. // but it generates too many false positives.
  6944. if (!allowNewLine) {
  6945. this.trigger("warning", {
  6946. code: "W112",
  6947. line: this.line,
  6948. character: this.char
  6949. });
  6950. } else {
  6951. allowNewLine = false;
  6952. // Otherwise show a warning if multistr option was not set.
  6953. // For JSON, show warning no matter what.
  6954. this.triggerAsync("warning", {
  6955. code: "W043",
  6956. line: this.line,
  6957. character: this.char
  6958. }, checks, function () { return !state.option.multistr; });
  6959. this.triggerAsync("warning", {
  6960. code: "W042",
  6961. line: this.line,
  6962. character: this.char
  6963. }, checks, function () { return state.jsonMode && state.option.multistr; });
  6964. }
  6965. // If we get an EOF inside of an unclosed string, show an
  6966. // error and implicitly close it at the EOF point.
  6967. if (!this.nextLine()) {
  6968. this.trigger("error", {
  6969. code: "E029",
  6970. line: startLine,
  6971. character: startChar
  6972. });
  6973. return {
  6974. type: Token.StringLiteral,
  6975. value: value,
  6976. isUnclosed: true,
  6977. quote: quote
  6978. };
  6979. }
  6980. if (this.peek() == quote)
  6981. break outer;
  6982. }
  6983. allowNewLine = false;
  6984. var char = this.peek();
  6985. var jump = 1; // A length of a jump, after we're done
  6986. // parsing this character.
  6987. if (char < " ") {
  6988. // Warn about a control character in a string.
  6989. this.trigger("warning", {
  6990. code: "W113",
  6991. line: this.line,
  6992. character: this.char,
  6993. data: [ "<non-printable>" ]
  6994. });
  6995. }
  6996. // Special treatment for some escaped characters.
  6997. if (char === "\\") {
  6998. this.skip();
  6999. char = this.peek();
  7000. switch (char) {
  7001. case "'":
  7002. this.triggerAsync("warning", {
  7003. code: "W114",
  7004. line: this.line,
  7005. character: this.char,
  7006. data: [ "\\'" ]
  7007. }, checks, function () {return state.jsonMode; });
  7008. break;
  7009. case "b":
  7010. char = "\b";
  7011. break;
  7012. case "f":
  7013. char = "\f";
  7014. break;
  7015. case "n":
  7016. char = "\n";
  7017. break;
  7018. case "r":
  7019. char = "\r";
  7020. break;
  7021. case "t":
  7022. char = "\t";
  7023. break;
  7024. case "0":
  7025. char = "\0";
  7026. // Octal literals fail in strict mode.
  7027. // Check if the number is between 00 and 07.
  7028. var n = parseInt(this.peek(1), 10);
  7029. this.triggerAsync("warning", {
  7030. code: "W115",
  7031. line: this.line,
  7032. character: this.char
  7033. }, checks,
  7034. function () { return n >= 0 && n <= 7 && state.directive["use strict"]; });
  7035. break;
  7036. case "u":
  7037. char = String.fromCharCode(parseInt(this.input.substr(1, 4), 16));
  7038. jump = 5;
  7039. break;
  7040. case "v":
  7041. this.triggerAsync("warning", {
  7042. code: "W114",
  7043. line: this.line,
  7044. character: this.char,
  7045. data: [ "\\v" ]
  7046. }, checks, function () { return state.jsonMode; });
  7047. char = "\v";
  7048. break;
  7049. case "x":
  7050. var x = parseInt(this.input.substr(1, 2), 16);
  7051. this.triggerAsync("warning", {
  7052. code: "W114",
  7053. line: this.line,
  7054. character: this.char,
  7055. data: [ "\\x-" ]
  7056. }, checks, function () { return state.jsonMode; });
  7057. char = String.fromCharCode(x);
  7058. jump = 3;
  7059. break;
  7060. case "\\":
  7061. case "\"":
  7062. case "/":
  7063. break;
  7064. case "":
  7065. allowNewLine = true;
  7066. char = "";
  7067. break;
  7068. case "!":
  7069. if (value.slice(value.length - 2) === "<") {
  7070. break;
  7071. }
  7072. /*falls through */
  7073. default:
  7074. // Weird escaping.
  7075. this.trigger("warning", {
  7076. code: "W044",
  7077. line: this.line,
  7078. character: this.char
  7079. });
  7080. }
  7081. }
  7082. value += char;
  7083. this.skip(jump);
  7084. }
  7085. this.skip();
  7086. return {
  7087. type: Token.StringLiteral,
  7088. value: value,
  7089. isUnclosed: false,
  7090. quote: quote
  7091. };
  7092. },
  7093. /*
  7094. * Extract a regular expression out of the next sequence of
  7095. * characters and/or lines or return 'null' if its not possible.
  7096. *
  7097. * This method is platform dependent: it accepts almost any
  7098. * regular expression values but then tries to compile and run
  7099. * them using system's RegExp object. This means that there are
  7100. * rare edge cases where one JavaScript engine complains about
  7101. * your regular expression while others don't.
  7102. */
  7103. scanRegExp: function () {
  7104. var index = 0;
  7105. var length = this.input.length;
  7106. var char = this.peek();
  7107. var value = char;
  7108. var body = "";
  7109. var flags = [];
  7110. var malformed = false;
  7111. var isCharSet = false;
  7112. var terminated;
  7113. var scanUnexpectedChars = function () {
  7114. // Unexpected control character
  7115. if (char < " ") {
  7116. malformed = true;
  7117. this.trigger("warning", {
  7118. code: "W048",
  7119. line: this.line,
  7120. character: this.char
  7121. });
  7122. }
  7123. // Unexpected escaped character
  7124. if (char === "<") {
  7125. malformed = true;
  7126. this.trigger("warning", {
  7127. code: "W049",
  7128. line: this.line,
  7129. character: this.char,
  7130. data: [ char ]
  7131. });
  7132. }
  7133. }.bind(this);
  7134. // Regular expressions must start with '/'
  7135. if (!this.prereg || char !== "/") {
  7136. return null;
  7137. }
  7138. index += 1;
  7139. terminated = false;
  7140. // Try to get everything in between slashes. A couple of
  7141. // cases aside (see scanUnexpectedChars) we don't really
  7142. // care whether the resulting expression is valid or not.
  7143. // We will check that later using the RegExp object.
  7144. while (index < length) {
  7145. char = this.peek(index);
  7146. value += char;
  7147. body += char;
  7148. if (isCharSet) {
  7149. if (char === "]") {
  7150. if (this.peek(index - 1) !== "\\" || this.peek(index - 2) === "\\") {
  7151. isCharSet = false;
  7152. }
  7153. }
  7154. if (char === "\\") {
  7155. index += 1;
  7156. char = this.peek(index);
  7157. body += char;
  7158. value += char;
  7159. scanUnexpectedChars();
  7160. }
  7161. index += 1;
  7162. continue;
  7163. }
  7164. if (char === "\\") {
  7165. index += 1;
  7166. char = this.peek(index);
  7167. body += char;
  7168. value += char;
  7169. scanUnexpectedChars();
  7170. if (char === "/") {
  7171. index += 1;
  7172. continue;
  7173. }
  7174. if (char === "[") {
  7175. index += 1;
  7176. continue;
  7177. }
  7178. }
  7179. if (char === "[") {
  7180. isCharSet = true;
  7181. index += 1;
  7182. continue;
  7183. }
  7184. if (char === "/") {
  7185. body = body.substr(0, body.length - 1);
  7186. terminated = true;
  7187. index += 1;
  7188. break;
  7189. }
  7190. index += 1;
  7191. }
  7192. // A regular expression that was never closed is an
  7193. // error from which we cannot recover.
  7194. if (!terminated) {
  7195. this.trigger("error", {
  7196. code: "E015",
  7197. line: this.line,
  7198. character: this.from
  7199. });
  7200. return void this.trigger("fatal", {
  7201. line: this.line,
  7202. from: this.from
  7203. });
  7204. }
  7205. // Parse flags (if any).
  7206. while (index < length) {
  7207. char = this.peek(index);
  7208. if (!/[gim]/.test(char)) {
  7209. break;
  7210. }
  7211. flags.push(char);
  7212. value += char;
  7213. index += 1;
  7214. }
  7215. // Check regular expression for correctness.
  7216. try {
  7217. new RegExp(body, flags.join(""));
  7218. } catch (err) {
  7219. malformed = true;
  7220. this.trigger("error", {
  7221. code: "E016",
  7222. line: this.line,
  7223. character: this.char,
  7224. data: [ err.message ] // Platform dependent!
  7225. });
  7226. }
  7227. return {
  7228. type: Token.RegExp,
  7229. value: value,
  7230. flags: flags,
  7231. isMalformed: malformed
  7232. };
  7233. },
  7234. /*
  7235. * Scan for any occurence of mixed tabs and spaces. If smarttabs option
  7236. * is on, ignore tabs followed by spaces.
  7237. *
  7238. * Tabs followed by one space followed by a block comment are allowed.
  7239. */
  7240. scanMixedSpacesAndTabs: function () {
  7241. var at, match;
  7242. if (state.option.smarttabs) {
  7243. // Negative look-behind for "//"
  7244. match = this.input.match(/(\/\/|^\s?\*)? \t/);
  7245. at = match && !match[1] ? 0 : -1;
  7246. } else {
  7247. at = this.input.search(/ \t|\t [^\*]/);
  7248. }
  7249. return at;
  7250. },
  7251. /*
  7252. * Scan for characters that get silently deleted by one or more browsers.
  7253. */
  7254. scanUnsafeChars: function () {
  7255. return this.input.search(reg.unsafeChars);
  7256. },
  7257. /*
  7258. * Produce the next raw token or return 'null' if no tokens can be matched.
  7259. * This method skips over all space characters.
  7260. */
  7261. next: function (checks) {
  7262. this.from = this.char;
  7263. // Move to the next non-space character.
  7264. var start;
  7265. if (/\s/.test(this.peek())) {
  7266. start = this.char;
  7267. while (/\s/.test(this.peek())) {
  7268. this.from += 1;
  7269. this.skip();
  7270. }
  7271. if (this.peek() === "") { // EOL
  7272. if (!/^\s*$/.test(this.getLines()[this.line - 1]) && state.option.trailing) {
  7273. this.trigger("warning", { code: "W102", line: this.line, character: start });
  7274. }
  7275. }
  7276. }
  7277. // Methods that work with multi-line structures and move the
  7278. // character pointer.
  7279. var match = this.scanComments() ||
  7280. this.scanStringLiteral(checks);
  7281. if (match) {
  7282. return match;
  7283. }
  7284. // Methods that don't move the character pointer.
  7285. match =
  7286. this.scanRegExp() ||
  7287. this.scanPunctuator() ||
  7288. this.scanKeyword() ||
  7289. this.scanIdentifier() ||
  7290. this.scanNumericLiteral();
  7291. if (match) {
  7292. this.skip(match.value.length);
  7293. return match;
  7294. }
  7295. // No token could be matched, give up.
  7296. return null;
  7297. },
  7298. /*
  7299. * Switch to the next line and reset all char pointers. Once
  7300. * switched, this method also checks for mixed spaces and tabs
  7301. * and other minor warnings.
  7302. */
  7303. nextLine: function () {
  7304. var char;
  7305. if (this.line >= this.getLines().length) {
  7306. return false;
  7307. }
  7308. this.input = this.getLines()[this.line];
  7309. this.line += 1;
  7310. this.char = 1;
  7311. this.from = 1;
  7312. char = this.scanMixedSpacesAndTabs();
  7313. if (char >= 0) {
  7314. this.trigger("warning", { code: "W099", line: this.line, character: char + 1 });
  7315. }
  7316. this.input = this.input.replace(/\t/g, state.tab);
  7317. char = this.scanUnsafeChars();
  7318. if (char >= 0) {
  7319. this.trigger("warning", { code: "W100", line: this.line, character: char });
  7320. }
  7321. // If there is a limit on line length, warn when lines get too
  7322. // long.
  7323. if (state.option.maxlen && state.option.maxlen < this.input.length) {
  7324. this.trigger("warning", { code: "W101", line: this.line, character: this.input.length });
  7325. }
  7326. return true;
  7327. },
  7328. /*
  7329. * This is simply a synonym for nextLine() method with a friendlier
  7330. * public name.
  7331. */
  7332. start: function () {
  7333. this.nextLine();
  7334. },
  7335. /*
  7336. * Produce the next token. This function is called by advance() to get
  7337. * the next token. It retuns a token in a JSLint-compatible format.
  7338. */
  7339. token: function () {
  7340. /*jshint loopfunc:true */
  7341. var checks = asyncTrigger();
  7342. var token;
  7343. function isReserved(token, isProperty) {
  7344. if (!token.reserved) {
  7345. return false;
  7346. }
  7347. var meta = token.meta;
  7348. if (meta && meta.isFutureReservedWord && state.option.inES5()) {
  7349. // ES3 FutureReservedWord in an ES5 environment.
  7350. if (!meta.es5) {
  7351. return false;
  7352. }
  7353. // Some ES5 FutureReservedWord identifiers are active only
  7354. // within a strict mode environment.
  7355. if (meta.strictOnly) {
  7356. if (!state.option.strict && !state.directive["use strict"]) {
  7357. return false;
  7358. }
  7359. }
  7360. if (isProperty) {
  7361. return false;
  7362. }
  7363. }
  7364. return true;
  7365. }
  7366. // Produce a token object.
  7367. var create = function (type, value, isProperty) {
  7368. /*jshint validthis:true */
  7369. var obj;
  7370. if (type !== "(endline)" && type !== "(end)") {
  7371. this.prereg = false;
  7372. }
  7373. if (type === "(punctuator)") {
  7374. switch (value) {
  7375. case ".":
  7376. case ")":
  7377. case "~":
  7378. case "#":
  7379. case "]":
  7380. this.prereg = false;
  7381. break;
  7382. default:
  7383. this.prereg = true;
  7384. }
  7385. obj = Object.create(state.syntax[value] || state.syntax["(error)"]);
  7386. }
  7387. if (type === "(identifier)") {
  7388. if (value === "return" || value === "case" || value === "typeof") {
  7389. this.prereg = true;
  7390. }
  7391. if (_.has(state.syntax, value)) {
  7392. obj = Object.create(state.syntax[value] || state.syntax["(error)"]);
  7393. // If this can't be a reserved keyword, reset the object.
  7394. if (!isReserved(obj, isProperty && type === "(identifier)")) {
  7395. obj = null;
  7396. }
  7397. }
  7398. }
  7399. if (!obj) {
  7400. obj = Object.create(state.syntax[type]);
  7401. }
  7402. obj.identifier = (type === "(identifier)");
  7403. obj.type = obj.type || type;
  7404. obj.value = value;
  7405. obj.line = this.line;
  7406. obj.character = this.char;
  7407. obj.from = this.from;
  7408. if (isProperty && obj.identifier) {
  7409. obj.isProperty = isProperty;
  7410. }
  7411. obj.check = checks.check;
  7412. return obj;
  7413. }.bind(this);
  7414. for (;;) {
  7415. if (!this.input.length) {
  7416. return create(this.nextLine() ? "(endline)" : "(end)", "");
  7417. }
  7418. token = this.next(checks);
  7419. if (!token) {
  7420. if (this.input.length) {
  7421. // Unexpected character.
  7422. this.trigger("error", {
  7423. code: "E024",
  7424. line: this.line,
  7425. character: this.char,
  7426. data: [ this.peek() ]
  7427. });
  7428. this.input = "";
  7429. }
  7430. continue;
  7431. }
  7432. switch (token.type) {
  7433. case Token.StringLiteral:
  7434. this.triggerAsync("String", {
  7435. line: this.line,
  7436. char: this.char,
  7437. from: this.from,
  7438. value: token.value,
  7439. quote: token.quote
  7440. }, checks, function () { return true; });
  7441. return create("(string)", token.value);
  7442. case Token.Identifier:
  7443. this.trigger("Identifier", {
  7444. line: this.line,
  7445. char: this.char,
  7446. from: this.form,
  7447. name: token.value,
  7448. isProperty: state.tokens.curr.id === "."
  7449. });
  7450. /* falls through */
  7451. case Token.Keyword:
  7452. case Token.NullLiteral:
  7453. case Token.BooleanLiteral:
  7454. return create("(identifier)", token.value, state.tokens.curr.id === ".");
  7455. case Token.NumericLiteral:
  7456. if (token.isMalformed) {
  7457. this.trigger("warning", {
  7458. code: "W045",
  7459. line: this.line,
  7460. character: this.char,
  7461. data: [ token.value ]
  7462. });
  7463. }
  7464. this.triggerAsync("warning", {
  7465. code: "W114",
  7466. line: this.line,
  7467. character: this.char,
  7468. data: [ "0x-" ]
  7469. }, checks, function () { return token.base === 16 && state.jsonMode; });
  7470. this.triggerAsync("warning", {
  7471. code: "W115",
  7472. line: this.line,
  7473. character: this.char
  7474. }, checks, function () {
  7475. return state.directive["use strict"] && token.base === 8;
  7476. });
  7477. this.trigger("Number", {
  7478. line: this.line,
  7479. char: this.char,
  7480. from: this.from,
  7481. value: token.value,
  7482. base: token.base,
  7483. isMalformed: token.malformed
  7484. });
  7485. return create("(number)", token.value);
  7486. case Token.RegExp:
  7487. return create("(regexp)", token.value);
  7488. case Token.Comment:
  7489. state.tokens.curr.comment = true;
  7490. if (token.isSpecial) {
  7491. return {
  7492. value: token.value,
  7493. body: token.body,
  7494. type: token.commentType,
  7495. isSpecial: token.isSpecial,
  7496. line: this.line,
  7497. character: this.char,
  7498. from: this.from
  7499. };
  7500. }
  7501. break;
  7502. case "":
  7503. break;
  7504. default:
  7505. return create("(punctuator)", token.value);
  7506. }
  7507. }
  7508. }
  7509. };
  7510. exports.Lexer = Lexer;
  7511. },
  7512. {"./reg.js":6,"./state.js":7,"events":10,"underscore":1}],
  7513. 6:[function(req,module,exports){
  7514. /*
  7515. * Regular expressions. Some of these are stupidly long.
  7516. */
  7517. /*jshint maxlen:1000 */
  7518. "use string";
  7519. // Unsafe comment or string (ax)
  7520. exports.unsafeString =
  7521. /@cc|<\/?|script|\]\s*\]|<\s*!|&lt/i;
  7522. // Unsafe characters that are silently deleted by one or more browsers (cx)
  7523. exports.unsafeChars =
  7524. /[\u0000-\u001f\u007f-\u009f\u00ad\u0600-\u0604\u070f\u17b4\u17b5\u200c-\u200f\u2028-\u202f\u2060-\u206f\ufeff\ufff0-\uffff]/;
  7525. // Characters in strings that need escaping (nx and nxg)
  7526. exports.needEsc =
  7527. /[\u0000-\u001f&<"\/\\\u007f-\u009f\u00ad\u0600-\u0604\u070f\u17b4\u17b5\u200c-\u200f\u2028-\u202f\u2060-\u206f\ufeff\ufff0-\uffff]/;
  7528. exports.needEscGlobal =
  7529. /[\u0000-\u001f&<"\/\\\u007f-\u009f\u00ad\u0600-\u0604\u070f\u17b4\u17b5\u200c-\u200f\u2028-\u202f\u2060-\u206f\ufeff\ufff0-\uffff]/g;
  7530. // Star slash (lx)
  7531. exports.starSlash = /\*\//;
  7532. // Identifier (ix)
  7533. exports.identifier = /^([a-zA-Z_$][a-zA-Z0-9_$]*)$/;
  7534. // JavaScript URL (jx)
  7535. exports.javascriptURL = /^(?:javascript|jscript|ecmascript|vbscript|mocha|livescript)\s*:/i;
  7536. // Catches /* falls through */ comments (ft)
  7537. exports.fallsThrough = /^\s*\/\*\s*falls?\sthrough\s*\*\/\s*$/;
  7538. },
  7539. {}],
  7540. 7:[function(req,module,exports){
  7541. "use strict";
  7542. var state = {
  7543. syntax: {},
  7544. reset: function () {
  7545. this.tokens = {
  7546. prev: null,
  7547. next: null,
  7548. curr: null
  7549. };
  7550. this.option = {};
  7551. this.ignored = {};
  7552. this.directive = {};
  7553. this.jsonMode = false;
  7554. this.jsonWarnings = [];
  7555. this.lines = [];
  7556. this.tab = "";
  7557. this.cache = {}; // Node.JS doesn't have Map. Sniff.
  7558. }
  7559. };
  7560. exports.state = state;
  7561. },
  7562. {}],
  7563. 8:[function(req,module,exports){
  7564. "use strict";
  7565. exports.register = function (linter) {
  7566. // Check for properties named __proto__. This special property was
  7567. // deprecated and then re-introduced for ES6.
  7568. linter.on("Identifier", function style_scanProto(data) {
  7569. if (linter.getOption("proto")) {
  7570. return;
  7571. }
  7572. if (data.name === "__proto__") {
  7573. linter.warn("W103", {
  7574. line: data.line,
  7575. char: data.char,
  7576. data: [ data.name ]
  7577. });
  7578. }
  7579. });
  7580. // Check for properties named __iterator__. This is a special property
  7581. // available only in browsers with JavaScript 1.7 implementation.
  7582. linter.on("Identifier", function style_scanIterator(data) {
  7583. if (linter.getOption("iterator")) {
  7584. return;
  7585. }
  7586. if (data.name === "__iterator__") {
  7587. linter.warn("W104", {
  7588. line: data.line,
  7589. char: data.char,
  7590. data: [ data.name ]
  7591. });
  7592. }
  7593. });
  7594. // Check for dangling underscores.
  7595. linter.on("Identifier", function style_scanDangling(data) {
  7596. if (!linter.getOption("nomen")) {
  7597. return;
  7598. }
  7599. // Underscore.js
  7600. if (data.name === "_") {
  7601. return;
  7602. }
  7603. // In Node, __dirname and __filename should be ignored.
  7604. if (linter.getOption("node")) {
  7605. if (/^(__dirname|__filename)$/.test(data.name) && !data.isProperty) {
  7606. return;
  7607. }
  7608. }
  7609. if (/^(_+.*|.*_+)$/.test(data.name)) {
  7610. linter.warn("W105", {
  7611. line: data.line,
  7612. char: data.from,
  7613. data: [ "dangling '_'", data.name ]
  7614. });
  7615. }
  7616. });
  7617. // Check that all identifiers are using camelCase notation.
  7618. // Exceptions: names like MY_VAR and _myVar.
  7619. linter.on("Identifier", function style_scanCamelCase(data) {
  7620. if (!linter.getOption("camelcase")) {
  7621. return;
  7622. }
  7623. if (data.name.replace(/^_+/, "").indexOf("_") > -1 && !data.name.match(/^[A-Z0-9_]*$/)) {
  7624. linter.warn("W106", {
  7625. line: data.line,
  7626. char: data.from,
  7627. data: [ data.name ]
  7628. });
  7629. }
  7630. });
  7631. // Enforce consistency in style of quoting.
  7632. linter.on("String", function style_scanQuotes(data) {
  7633. var quotmark = linter.getOption("quotmark");
  7634. var code;
  7635. if (!quotmark) {
  7636. return;
  7637. }
  7638. // If quotmark is set to 'single' warn about all double-quotes.
  7639. if (quotmark === "single" && data.quote !== "'") {
  7640. code = "W109";
  7641. }
  7642. // If quotmark is set to 'double' warn about all single-quotes.
  7643. if (quotmark === "double" && data.quote !== "\"") {
  7644. code = "W108";
  7645. }
  7646. // If quotmark is set to true, remember the first quotation style
  7647. // and then warn about all others.
  7648. if (quotmark === true) {
  7649. if (!linter.getCache("quotmark")) {
  7650. linter.setCache("quotmark", data.quote);
  7651. }
  7652. if (linter.getCache("quotmark") !== data.quote) {
  7653. code = "W110";
  7654. }
  7655. }
  7656. if (code) {
  7657. linter.warn(code, {
  7658. line: data.line,
  7659. char: data.char,
  7660. });
  7661. }
  7662. });
  7663. linter.on("Number", function style_scanNumbers(data) {
  7664. if (data.value.charAt(0) === ".") {
  7665. // Warn about a leading decimal point.
  7666. linter.warn("W008", {
  7667. line: data.line,
  7668. char: data.char,
  7669. data: [ data.value ]
  7670. });
  7671. }
  7672. if (data.value.substr(data.value.length - 1) === ".") {
  7673. // Warn about a trailing decimal point.
  7674. linter.warn("W047", {
  7675. line: data.line,
  7676. char: data.char,
  7677. data: [ data.value ]
  7678. });
  7679. }
  7680. if (/^00+/.test(data.value)) {
  7681. // Multiple leading zeroes.
  7682. linter.warn("W046", {
  7683. line: data.line,
  7684. char: data.char,
  7685. data: [ data.value ]
  7686. });
  7687. }
  7688. });
  7689. // Warn about script URLs.
  7690. linter.on("String", function style_scanJavaScriptURLs(data) {
  7691. var re = /^(?:javascript|jscript|ecmascript|vbscript|mocha|livescript)\s*:/i;
  7692. if (linter.getOption("scripturl")) {
  7693. return;
  7694. }
  7695. if (re.test(data.value)) {
  7696. linter.warn("W107", {
  7697. line: data.line,
  7698. char: data.char
  7699. });
  7700. }
  7701. });
  7702. };
  7703. },
  7704. {}],
  7705. 9:[function(req,module,exports){
  7706. },
  7707. {}],
  7708. 10:[function(req,module,exports){
  7709. var process=req("__browserify_process");if (!process.EventEmitter) process.EventEmitter = function () {};
  7710. var EventEmitter = exports.EventEmitter = process.EventEmitter;
  7711. var isArray = typeof Array.isArray === 'function'
  7712. ? Array.isArray
  7713. : function (xs) {
  7714. return Object.prototype.toString.call(xs) === '[object Array]'
  7715. }
  7716. ;
  7717. function indexOf (xs, x) {
  7718. if (xs.indexOf) return xs.indexOf(x);
  7719. for (var i = 0; i < xs.length; i++) {
  7720. if (x === xs[i]) return i;
  7721. }
  7722. return -1;
  7723. }
  7724. // By default EventEmitters will print a warning if more than
  7725. // 10 listeners are added to it. This is a useful default which
  7726. // helps finding memory leaks.
  7727. //
  7728. // Obviously not all Emitters should be limited to 10. This function allows
  7729. // that to be increased. Set to zero for unlimited.
  7730. var defaultMaxListeners = 200;
  7731. EventEmitter.prototype.setMaxListeners = function(n) {
  7732. if (!this._events) this._events = {};
  7733. this._events.maxListeners = n;
  7734. };
  7735. EventEmitter.prototype.emit = function(type) {
  7736. // If there is no 'error' event listener then throw.
  7737. if (type === 'error') {
  7738. if (!this._events || !this._events.error ||
  7739. (isArray(this._events.error) && !this._events.error.length))
  7740. {
  7741. if (arguments[1] instanceof Error) {
  7742. throw arguments[1]; // Unhandled 'error' event
  7743. } else {
  7744. throw new Error("Uncaught, unspecified 'error' event.");
  7745. }
  7746. return false;
  7747. }
  7748. }
  7749. if (!this._events) return false;
  7750. var handler = this._events[type];
  7751. if (!handler) return false;
  7752. if (typeof handler == 'function') {
  7753. switch (arguments.length) {
  7754. // fast cases
  7755. case 1:
  7756. handler.call(this);
  7757. break;
  7758. case 2:
  7759. handler.call(this, arguments[1]);
  7760. break;
  7761. case 3:
  7762. handler.call(this, arguments[1], arguments[2]);
  7763. break;
  7764. // slower
  7765. default:
  7766. var args = Array.prototype.slice.call(arguments, 1);
  7767. handler.apply(this, args);
  7768. }
  7769. return true;
  7770. } else if (isArray(handler)) {
  7771. var args = Array.prototype.slice.call(arguments, 1);
  7772. var listeners = handler.slice();
  7773. for (var i = 0, l = listeners.length; i < l; i++) {
  7774. listeners[i].apply(this, args);
  7775. }
  7776. return true;
  7777. } else {
  7778. return false;
  7779. }
  7780. };
  7781. // EventEmitter is defined in src/node_events.cc
  7782. // EventEmitter.prototype.emit() is also defined there.
  7783. EventEmitter.prototype.addListener = function(type, listener) {
  7784. if ('function' !== typeof listener) {
  7785. throw new Error('addListener only takes instances of Function');
  7786. }
  7787. if (!this._events) this._events = {};
  7788. // To avoid recursion in the case that type == "newListeners"! Before
  7789. // adding it to the listeners, first emit "newListeners".
  7790. this.emit('newListener', type, listener);
  7791. if (!this._events[type]) {
  7792. // Optimize the case of one listener. Don't need the extra array object.
  7793. this._events[type] = listener;
  7794. } else if (isArray(this._events[type])) {
  7795. // Check for listener leak
  7796. if (!this._events[type].warned) {
  7797. var m;
  7798. if (this._events.maxListeners !== undefined) {
  7799. m = this._events.maxListeners;
  7800. } else {
  7801. m = defaultMaxListeners;
  7802. }
  7803. if (m && m > 0 && this._events[type].length > m) {
  7804. this._events[type].warned = true;
  7805. console.error('(node) warning: possible EventEmitter memory ' +
  7806. 'leak detected. %d listeners added. ' +
  7807. 'Use emitter.setMaxListeners() to increase limit.',
  7808. this._events[type].length);
  7809. console.trace();
  7810. }
  7811. }
  7812. // If we've already got an array, just append.
  7813. this._events[type].push(listener);
  7814. } else {
  7815. // Adding the second element, need to change to array.
  7816. this._events[type] = [this._events[type], listener];
  7817. }
  7818. return this;
  7819. };
  7820. EventEmitter.prototype.on = EventEmitter.prototype.addListener;
  7821. EventEmitter.prototype.once = function(type, listener) {
  7822. var self = this;
  7823. self.on(type, function g() {
  7824. self.removeListener(type, g);
  7825. listener.apply(this, arguments);
  7826. });
  7827. return this;
  7828. };
  7829. EventEmitter.prototype.removeListener = function(type, listener) {
  7830. if ('function' !== typeof listener) {
  7831. throw new Error('removeListener only takes instances of Function');
  7832. }
  7833. // does not use listeners(), so no side effect of creating _events[type]
  7834. if (!this._events || !this._events[type]) return this;
  7835. var list = this._events[type];
  7836. if (isArray(list)) {
  7837. var i = indexOf(list, listener);
  7838. if (i < 0) return this;
  7839. list.splice(i, 1);
  7840. if (list.length == 0)
  7841. delete this._events[type];
  7842. } else if (this._events[type] === listener) {
  7843. delete this._events[type];
  7844. }
  7845. return this;
  7846. };
  7847. EventEmitter.prototype.removeAllListeners = function(type) {
  7848. if (arguments.length === 0) {
  7849. this._events = {};
  7850. return this;
  7851. }
  7852. // does not use listeners(), so no side effect of creating _events[type]
  7853. if (type && this._events && this._events[type]) this._events[type] = null;
  7854. return this;
  7855. };
  7856. EventEmitter.prototype.listeners = function(type) {
  7857. if (!this._events) this._events = {};
  7858. if (!this._events[type]) this._events[type] = [];
  7859. if (!isArray(this._events[type])) {
  7860. this._events[type] = [this._events[type]];
  7861. }
  7862. return this._events[type];
  7863. };
  7864. EventEmitter.listenerCount = function(emitter, type) {
  7865. var ret;
  7866. if (!emitter._events || !emitter._events[type])
  7867. ret = 0;
  7868. else if (typeof emitter._events[type] === 'function')
  7869. ret = 1;
  7870. else
  7871. ret = emitter._events[type].length;
  7872. return ret;
  7873. };
  7874. },
  7875. {"__browserify_process":11}],
  7876. 11:[function(req,module,exports){
  7877. // shim for using process in browser
  7878. var process = module.exports = {};
  7879. process.nextTick = (function () {
  7880. var canSetImmediate = typeof window !== 'undefined'
  7881. && window.setImmediate;
  7882. var canPost = typeof window !== 'undefined'
  7883. && window.postMessage && window.addEventListener
  7884. ;
  7885. if (canSetImmediate) {
  7886. return function (f) { return window.setImmediate(f) };
  7887. }
  7888. if (canPost) {
  7889. var queue = [];
  7890. window.addEventListener('message', function (ev) {
  7891. if (ev.source === window && ev.data === 'process-tick') {
  7892. ev.stopPropagation();
  7893. if (queue.length > 0) {
  7894. var fn = queue.shift();
  7895. fn();
  7896. }
  7897. }
  7898. }, true);
  7899. return function nextTick(fn) {
  7900. queue.push(fn);
  7901. window.postMessage('process-tick', '*');
  7902. };
  7903. }
  7904. return function nextTick(fn) {
  7905. setTimeout(fn, 0);
  7906. };
  7907. })();
  7908. process.title = 'browser';
  7909. process.browser = true;
  7910. process.env = {};
  7911. process.argv = [];
  7912. process.binding = function (name) {
  7913. throw new Error('process.binding is not supported');
  7914. }
  7915. // TODO(shtylman)
  7916. process.cwd = function () { return '/' };
  7917. process.chdir = function (dir) {
  7918. throw new Error('process.chdir is not supported');
  7919. };
  7920. },
  7921. {}],
  7922. "jshint":[function(req,module,exports){
  7923. module.exports=req('n4bKNg');
  7924. },
  7925. {}]},{},["n4bKNg"])
  7926. ;
  7927. function req() {return require.apply(this, arguments)}
  7928. module.exports = req("jshint");
  7929. });