syscall.c 189 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341234223432344234523462347234823492350235123522353235423552356235723582359236023612362236323642365236623672368236923702371237223732374237523762377237823792380238123822383238423852386238723882389239023912392239323942395239623972398239924002401240224032404240524062407240824092410241124122413241424152416241724182419242024212422242324242425242624272428242924302431243224332434243524362437243824392440244124422443244424452446244724482449245024512452245324542455245624572458245924602461246224632464246524662467246824692470247124722473247424752476247724782479248024812482248324842485248624872488248924902491249224932494249524962497249824992500250125022503250425052506250725082509251025112512251325142515251625172518251925202521252225232524252525262527252825292530253125322533253425352536253725382539254025412542254325442545254625472548254925502551255225532554255525562557255825592560256125622563256425652566256725682569257025712572257325742575257625772578257925802581258225832584258525862587258825892590259125922593259425952596259725982599260026012602260326042605260626072608260926102611261226132614261526162617261826192620262126222623262426252626262726282629263026312632263326342635263626372638263926402641264226432644264526462647264826492650265126522653265426552656265726582659266026612662266326642665266626672668266926702671267226732674267526762677267826792680268126822683268426852686268726882689269026912692269326942695269626972698269927002701270227032704270527062707270827092710271127122713271427152716271727182719272027212722272327242725272627272728272927302731273227332734273527362737273827392740274127422743274427452746274727482749275027512752275327542755275627572758275927602761276227632764276527662767276827692770277127722773277427752776277727782779278027812782278327842785278627872788278927902791279227932794279527962797279827992800280128022803280428052806280728082809281028112812281328142815281628172818281928202821282228232824282528262827282828292830283128322833283428352836283728382839284028412842284328442845284628472848284928502851285228532854285528562857285828592860286128622863286428652866286728682869287028712872287328742875287628772878287928802881288228832884288528862887288828892890289128922893289428952896289728982899290029012902290329042905290629072908290929102911291229132914291529162917291829192920292129222923292429252926292729282929293029312932293329342935293629372938293929402941294229432944294529462947294829492950295129522953295429552956295729582959296029612962296329642965296629672968296929702971297229732974297529762977297829792980298129822983298429852986298729882989299029912992299329942995299629972998299930003001300230033004300530063007300830093010301130123013301430153016301730183019302030213022302330243025302630273028302930303031303230333034303530363037303830393040304130423043304430453046304730483049305030513052305330543055305630573058305930603061306230633064306530663067306830693070307130723073307430753076307730783079308030813082308330843085308630873088308930903091309230933094309530963097309830993100310131023103310431053106310731083109311031113112311331143115311631173118311931203121312231233124312531263127312831293130313131323133313431353136313731383139314031413142314331443145314631473148314931503151315231533154315531563157315831593160316131623163316431653166316731683169317031713172317331743175317631773178317931803181318231833184318531863187318831893190319131923193319431953196319731983199320032013202320332043205320632073208320932103211321232133214321532163217321832193220322132223223322432253226322732283229323032313232323332343235323632373238323932403241324232433244324532463247324832493250325132523253325432553256325732583259326032613262326332643265326632673268326932703271327232733274327532763277327832793280328132823283328432853286328732883289329032913292329332943295329632973298329933003301330233033304330533063307330833093310331133123313331433153316331733183319332033213322332333243325332633273328332933303331333233333334333533363337333833393340334133423343334433453346334733483349335033513352335333543355335633573358335933603361336233633364336533663367336833693370337133723373337433753376337733783379338033813382338333843385338633873388338933903391339233933394339533963397339833993400340134023403340434053406340734083409341034113412341334143415341634173418341934203421342234233424342534263427342834293430343134323433343434353436343734383439344034413442344334443445344634473448344934503451345234533454345534563457345834593460346134623463346434653466346734683469347034713472347334743475347634773478347934803481348234833484348534863487348834893490349134923493349434953496349734983499350035013502350335043505350635073508350935103511351235133514351535163517351835193520352135223523352435253526352735283529353035313532353335343535353635373538353935403541354235433544354535463547354835493550355135523553355435553556355735583559356035613562356335643565356635673568356935703571357235733574357535763577357835793580358135823583358435853586358735883589359035913592359335943595359635973598359936003601360236033604360536063607360836093610361136123613361436153616361736183619362036213622362336243625362636273628362936303631363236333634363536363637363836393640364136423643364436453646364736483649365036513652365336543655365636573658365936603661366236633664366536663667366836693670367136723673367436753676367736783679368036813682368336843685368636873688368936903691369236933694369536963697369836993700370137023703370437053706370737083709371037113712371337143715371637173718371937203721372237233724372537263727372837293730373137323733373437353736373737383739374037413742374337443745374637473748374937503751375237533754375537563757375837593760376137623763376437653766376737683769377037713772377337743775377637773778377937803781378237833784378537863787378837893790379137923793379437953796379737983799380038013802380338043805380638073808380938103811381238133814381538163817381838193820382138223823382438253826382738283829383038313832383338343835383638373838383938403841384238433844384538463847384838493850385138523853385438553856385738583859386038613862386338643865386638673868386938703871387238733874387538763877387838793880388138823883388438853886388738883889389038913892389338943895389638973898389939003901390239033904390539063907390839093910391139123913391439153916391739183919392039213922392339243925392639273928392939303931393239333934393539363937393839393940394139423943394439453946394739483949395039513952395339543955395639573958395939603961396239633964396539663967396839693970397139723973397439753976397739783979398039813982398339843985398639873988398939903991399239933994399539963997399839994000400140024003400440054006400740084009401040114012401340144015401640174018401940204021402240234024402540264027402840294030403140324033403440354036403740384039404040414042404340444045404640474048404940504051405240534054405540564057405840594060406140624063406440654066406740684069407040714072407340744075407640774078407940804081408240834084408540864087408840894090409140924093409440954096409740984099410041014102410341044105410641074108410941104111411241134114411541164117411841194120412141224123412441254126412741284129413041314132413341344135413641374138413941404141414241434144414541464147414841494150415141524153415441554156415741584159416041614162416341644165416641674168416941704171417241734174417541764177417841794180418141824183418441854186418741884189419041914192419341944195419641974198419942004201420242034204420542064207420842094210421142124213421442154216421742184219422042214222422342244225422642274228422942304231423242334234423542364237423842394240424142424243424442454246424742484249425042514252425342544255425642574258425942604261426242634264426542664267426842694270427142724273427442754276427742784279428042814282428342844285428642874288428942904291429242934294429542964297429842994300430143024303430443054306430743084309431043114312431343144315431643174318431943204321432243234324432543264327432843294330433143324333433443354336433743384339434043414342434343444345434643474348434943504351435243534354435543564357435843594360436143624363436443654366436743684369437043714372437343744375437643774378437943804381438243834384438543864387438843894390439143924393439443954396439743984399440044014402440344044405440644074408440944104411441244134414441544164417441844194420442144224423442444254426442744284429443044314432443344344435443644374438443944404441444244434444444544464447444844494450445144524453445444554456445744584459446044614462446344644465446644674468446944704471447244734474447544764477447844794480448144824483448444854486448744884489449044914492449344944495449644974498449945004501450245034504450545064507450845094510451145124513451445154516451745184519452045214522452345244525452645274528452945304531453245334534453545364537453845394540454145424543454445454546454745484549455045514552455345544555455645574558455945604561456245634564456545664567456845694570457145724573457445754576457745784579458045814582458345844585458645874588458945904591459245934594459545964597459845994600460146024603460446054606460746084609461046114612461346144615461646174618461946204621462246234624462546264627462846294630463146324633463446354636463746384639464046414642464346444645464646474648464946504651465246534654465546564657465846594660466146624663466446654666466746684669467046714672467346744675467646774678467946804681468246834684468546864687468846894690469146924693469446954696469746984699470047014702470347044705470647074708470947104711471247134714471547164717471847194720472147224723472447254726472747284729473047314732473347344735473647374738473947404741474247434744474547464747474847494750475147524753475447554756475747584759476047614762476347644765476647674768476947704771477247734774477547764777477847794780478147824783478447854786478747884789479047914792479347944795479647974798479948004801480248034804480548064807480848094810481148124813481448154816481748184819482048214822482348244825482648274828482948304831483248334834483548364837483848394840484148424843484448454846484748484849485048514852485348544855485648574858485948604861486248634864486548664867486848694870487148724873487448754876487748784879488048814882488348844885488648874888488948904891489248934894489548964897489848994900490149024903490449054906490749084909491049114912491349144915491649174918491949204921492249234924492549264927492849294930493149324933493449354936493749384939494049414942494349444945494649474948494949504951495249534954495549564957495849594960496149624963496449654966496749684969497049714972497349744975497649774978497949804981498249834984498549864987498849894990499149924993499449954996499749984999500050015002500350045005500650075008500950105011501250135014501550165017501850195020502150225023502450255026502750285029503050315032503350345035503650375038503950405041504250435044504550465047504850495050505150525053505450555056505750585059506050615062506350645065506650675068506950705071507250735074507550765077507850795080508150825083508450855086508750885089509050915092509350945095509650975098509951005101510251035104510551065107510851095110511151125113511451155116511751185119512051215122512351245125512651275128512951305131513251335134513551365137513851395140514151425143514451455146514751485149515051515152515351545155515651575158515951605161516251635164516551665167516851695170517151725173517451755176517751785179518051815182518351845185518651875188518951905191519251935194519551965197519851995200520152025203520452055206520752085209521052115212521352145215521652175218521952205221522252235224522552265227522852295230523152325233523452355236523752385239524052415242524352445245524652475248524952505251525252535254525552565257525852595260526152625263526452655266526752685269527052715272527352745275527652775278527952805281528252835284528552865287528852895290529152925293529452955296529752985299530053015302530353045305530653075308530953105311531253135314531553165317531853195320532153225323532453255326532753285329533053315332533353345335533653375338533953405341534253435344534553465347534853495350535153525353535453555356535753585359536053615362536353645365536653675368536953705371537253735374537553765377537853795380538153825383538453855386538753885389539053915392539353945395539653975398539954005401540254035404540554065407540854095410541154125413541454155416541754185419542054215422542354245425542654275428542954305431543254335434543554365437543854395440544154425443544454455446544754485449545054515452545354545455545654575458545954605461546254635464546554665467546854695470547154725473547454755476547754785479548054815482548354845485548654875488548954905491549254935494549554965497549854995500550155025503550455055506550755085509551055115512551355145515551655175518551955205521552255235524552555265527552855295530553155325533553455355536553755385539554055415542554355445545554655475548554955505551555255535554555555565557555855595560556155625563556455655566556755685569557055715572557355745575557655775578557955805581558255835584558555865587558855895590559155925593559455955596559755985599560056015602560356045605560656075608560956105611561256135614561556165617561856195620562156225623562456255626562756285629563056315632563356345635563656375638563956405641564256435644564556465647564856495650565156525653565456555656565756585659566056615662566356645665566656675668566956705671567256735674567556765677567856795680568156825683568456855686568756885689569056915692569356945695569656975698569957005701570257035704570557065707570857095710571157125713571457155716571757185719572057215722572357245725572657275728572957305731573257335734573557365737573857395740574157425743574457455746574757485749575057515752575357545755575657575758575957605761576257635764576557665767576857695770577157725773577457755776577757785779578057815782578357845785578657875788578957905791579257935794579557965797579857995800580158025803580458055806580758085809581058115812581358145815581658175818581958205821582258235824582558265827582858295830583158325833583458355836583758385839584058415842584358445845584658475848584958505851585258535854585558565857585858595860586158625863586458655866586758685869587058715872587358745875587658775878587958805881588258835884588558865887588858895890589158925893589458955896589758985899590059015902590359045905590659075908590959105911591259135914591559165917591859195920592159225923592459255926592759285929593059315932593359345935593659375938593959405941594259435944594559465947594859495950595159525953595459555956595759585959596059615962596359645965596659675968596959705971597259735974597559765977597859795980598159825983598459855986598759885989599059915992599359945995599659975998599960006001600260036004600560066007600860096010601160126013601460156016601760186019602060216022602360246025602660276028602960306031603260336034603560366037603860396040604160426043604460456046604760486049605060516052605360546055605660576058605960606061606260636064606560666067606860696070607160726073607460756076607760786079608060816082608360846085608660876088608960906091609260936094609560966097609860996100610161026103610461056106610761086109611061116112
  1. /*
  2. * Linux syscalls
  3. *
  4. * Copyright (c) 2003 Fabrice Bellard
  5. *
  6. * This program is free software; you can redistribute it and/or modify
  7. * it under the terms of the GNU General Public License as published by
  8. * the Free Software Foundation; either version 2 of the License, or
  9. * (at your option) any later version.
  10. *
  11. * This program is distributed in the hope that it will be useful,
  12. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  14. * GNU General Public License for more details.
  15. *
  16. * You should have received a copy of the GNU General Public License
  17. * along with this program; if not, write to the Free Software
  18. * Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
  19. * MA 02110-1301, USA.
  20. */
  21. #include <stdlib.h>
  22. #include <stdio.h>
  23. #include <stdarg.h>
  24. #include <string.h>
  25. #include <elf.h>
  26. #include <endian.h>
  27. #include <errno.h>
  28. #include <unistd.h>
  29. #include <fcntl.h>
  30. #include <time.h>
  31. #include <limits.h>
  32. #include <sys/types.h>
  33. #include <sys/ipc.h>
  34. #include <sys/msg.h>
  35. #include <sys/wait.h>
  36. #include <sys/time.h>
  37. #include <sys/stat.h>
  38. #include <sys/mount.h>
  39. #include <sys/prctl.h>
  40. #include <sys/resource.h>
  41. #include <sys/mman.h>
  42. #include <sys/swap.h>
  43. #include <signal.h>
  44. #include <sched.h>
  45. #include <sys/socket.h>
  46. #include <sys/uio.h>
  47. #include <sys/poll.h>
  48. #include <sys/times.h>
  49. #include <sys/shm.h>
  50. #include <sys/sem.h>
  51. #include <sys/statfs.h>
  52. #include <utime.h>
  53. #include <sys/sysinfo.h>
  54. //#include <sys/user.h>
  55. #include <netinet/ip.h>
  56. #include <netinet/tcp.h>
  57. #include <qemu-common.h>
  58. #ifdef HAVE_GPROF
  59. #include <sys/gmon.h>
  60. #endif
  61. #define termios host_termios
  62. #define winsize host_winsize
  63. #define termio host_termio
  64. #define sgttyb host_sgttyb /* same as target */
  65. #define tchars host_tchars /* same as target */
  66. #define ltchars host_ltchars /* same as target */
  67. #include <linux/termios.h>
  68. #include <linux/unistd.h>
  69. #include <linux/utsname.h>
  70. #include <linux/cdrom.h>
  71. #include <linux/hdreg.h>
  72. #include <linux/soundcard.h>
  73. #include <linux/kd.h>
  74. #include <linux/mtio.h>
  75. #include "linux_loop.h"
  76. #include "qemu.h"
  77. #include "qemu-common.h"
  78. #if defined(USE_NPTL)
  79. #include <linux/futex.h>
  80. #define CLONE_NPTL_FLAGS2 (CLONE_SETTLS | \
  81. CLONE_PARENT_SETTID | CLONE_CHILD_SETTID | CLONE_CHILD_CLEARTID)
  82. #else
  83. /* XXX: Hardcode the above values. */
  84. #define CLONE_NPTL_FLAGS2 0
  85. #endif
  86. //#define DEBUG
  87. #if defined(TARGET_I386) || defined(TARGET_ARM) || defined(TARGET_SPARC) \
  88. || defined(TARGET_M68K) || defined(TARGET_SH4) || defined(TARGET_CRIS)
  89. /* 16 bit uid wrappers emulation */
  90. #define USE_UID16
  91. #endif
  92. //#include <linux/msdos_fs.h>
  93. #define VFAT_IOCTL_READDIR_BOTH _IOR('r', 1, struct linux_dirent [2])
  94. #define VFAT_IOCTL_READDIR_SHORT _IOR('r', 2, struct linux_dirent [2])
  95. #undef _syscall0
  96. #undef _syscall1
  97. #undef _syscall2
  98. #undef _syscall3
  99. #undef _syscall4
  100. #undef _syscall5
  101. #undef _syscall6
  102. #define _syscall0(type,name) \
  103. static type name (void) \
  104. { \
  105. return syscall(__NR_##name); \
  106. }
  107. #define _syscall1(type,name,type1,arg1) \
  108. static type name (type1 arg1) \
  109. { \
  110. return syscall(__NR_##name, arg1); \
  111. }
  112. #define _syscall2(type,name,type1,arg1,type2,arg2) \
  113. static type name (type1 arg1,type2 arg2) \
  114. { \
  115. return syscall(__NR_##name, arg1, arg2); \
  116. }
  117. #define _syscall3(type,name,type1,arg1,type2,arg2,type3,arg3) \
  118. static type name (type1 arg1,type2 arg2,type3 arg3) \
  119. { \
  120. return syscall(__NR_##name, arg1, arg2, arg3); \
  121. }
  122. #define _syscall4(type,name,type1,arg1,type2,arg2,type3,arg3,type4,arg4) \
  123. static type name (type1 arg1,type2 arg2,type3 arg3,type4 arg4) \
  124. { \
  125. return syscall(__NR_##name, arg1, arg2, arg3, arg4); \
  126. }
  127. #define _syscall5(type,name,type1,arg1,type2,arg2,type3,arg3,type4,arg4, \
  128. type5,arg5) \
  129. static type name (type1 arg1,type2 arg2,type3 arg3,type4 arg4,type5 arg5) \
  130. { \
  131. return syscall(__NR_##name, arg1, arg2, arg3, arg4, arg5); \
  132. }
  133. #define _syscall6(type,name,type1,arg1,type2,arg2,type3,arg3,type4,arg4, \
  134. type5,arg5,type6,arg6) \
  135. static type name (type1 arg1,type2 arg2,type3 arg3,type4 arg4,type5 arg5, \
  136. type6 arg6) \
  137. { \
  138. return syscall(__NR_##name, arg1, arg2, arg3, arg4, arg5, arg6); \
  139. }
  140. #define __NR_sys_exit __NR_exit
  141. #define __NR_sys_uname __NR_uname
  142. #define __NR_sys_faccessat __NR_faccessat
  143. #define __NR_sys_fchmodat __NR_fchmodat
  144. #define __NR_sys_fchownat __NR_fchownat
  145. #define __NR_sys_fstatat64 __NR_fstatat64
  146. #define __NR_sys_futimesat __NR_futimesat
  147. #define __NR_sys_getcwd1 __NR_getcwd
  148. #define __NR_sys_getdents __NR_getdents
  149. #define __NR_sys_getdents64 __NR_getdents64
  150. #define __NR_sys_getpriority __NR_getpriority
  151. #define __NR_sys_linkat __NR_linkat
  152. #define __NR_sys_mkdirat __NR_mkdirat
  153. #define __NR_sys_mknodat __NR_mknodat
  154. #define __NR_sys_openat __NR_openat
  155. #define __NR_sys_readlinkat __NR_readlinkat
  156. #define __NR_sys_renameat __NR_renameat
  157. #define __NR_sys_rt_sigqueueinfo __NR_rt_sigqueueinfo
  158. #define __NR_sys_symlinkat __NR_symlinkat
  159. #define __NR_sys_syslog __NR_syslog
  160. #define __NR_sys_tgkill __NR_tgkill
  161. #define __NR_sys_tkill __NR_tkill
  162. #define __NR_sys_unlinkat __NR_unlinkat
  163. #define __NR_sys_utimensat __NR_utimensat
  164. #define __NR_sys_futex __NR_futex
  165. #define __NR_sys_inotify_init __NR_inotify_init
  166. #define __NR_sys_inotify_add_watch __NR_inotify_add_watch
  167. #define __NR_sys_inotify_rm_watch __NR_inotify_rm_watch
  168. #if defined(__alpha__) || defined (__ia64__) || defined(__x86_64__)
  169. #define __NR__llseek __NR_lseek
  170. #endif
  171. #ifdef __NR_gettid
  172. _syscall0(int, gettid)
  173. #else
  174. /* This is a replacement for the host gettid() and must return a host
  175. errno. */
  176. static int gettid(void) {
  177. return -ENOSYS;
  178. }
  179. #endif
  180. _syscall1(int,sys_exit,int,status)
  181. _syscall1(int,sys_uname,struct new_utsname *,buf)
  182. #if defined(TARGET_NR_faccessat) && defined(__NR_faccessat)
  183. _syscall4(int,sys_faccessat,int,dirfd,const char *,pathname,int,mode,int,flags)
  184. #endif
  185. #if defined(TARGET_NR_fchmodat) && defined(__NR_fchmodat)
  186. _syscall4(int,sys_fchmodat,int,dirfd,const char *,pathname,
  187. mode_t,mode,int,flags)
  188. #endif
  189. #if defined(TARGET_NR_fchownat) && defined(__NR_fchownat) && defined(USE_UID16)
  190. _syscall5(int,sys_fchownat,int,dirfd,const char *,pathname,
  191. uid_t,owner,gid_t,group,int,flags)
  192. #endif
  193. #if defined(TARGET_NR_fstatat64) && defined(__NR_fstatat64)
  194. _syscall4(int,sys_fstatat64,int,dirfd,const char *,pathname,
  195. struct stat *,buf,int,flags)
  196. #endif
  197. #if defined(TARGET_NR_futimesat) && defined(__NR_futimesat)
  198. _syscall3(int,sys_futimesat,int,dirfd,const char *,pathname,
  199. const struct timeval *,times)
  200. #endif
  201. _syscall2(int,sys_getcwd1,char *,buf,size_t,size)
  202. #if TARGET_ABI_BITS == 32
  203. _syscall3(int, sys_getdents, uint, fd, struct linux_dirent *, dirp, uint, count);
  204. #endif
  205. #if defined(TARGET_NR_getdents64) && defined(__NR_getdents64)
  206. _syscall3(int, sys_getdents64, uint, fd, struct linux_dirent64 *, dirp, uint, count);
  207. #endif
  208. _syscall2(int, sys_getpriority, int, which, int, who);
  209. #if !defined (__x86_64__)
  210. _syscall5(int, _llseek, uint, fd, ulong, hi, ulong, lo,
  211. loff_t *, res, uint, wh);
  212. #endif
  213. #if defined(TARGET_NR_linkat) && defined(__NR_linkat)
  214. _syscall5(int,sys_linkat,int,olddirfd,const char *,oldpath,
  215. int,newdirfd,const char *,newpath,int,flags)
  216. #endif
  217. #if defined(TARGET_NR_mkdirat) && defined(__NR_mkdirat)
  218. _syscall3(int,sys_mkdirat,int,dirfd,const char *,pathname,mode_t,mode)
  219. #endif
  220. #if defined(TARGET_NR_mknodat) && defined(__NR_mknodat)
  221. _syscall4(int,sys_mknodat,int,dirfd,const char *,pathname,
  222. mode_t,mode,dev_t,dev)
  223. #endif
  224. #if defined(TARGET_NR_openat) && defined(__NR_openat)
  225. _syscall4(int,sys_openat,int,dirfd,const char *,pathname,int,flags,mode_t,mode)
  226. #endif
  227. #if defined(TARGET_NR_readlinkat) && defined(__NR_readlinkat)
  228. _syscall4(int,sys_readlinkat,int,dirfd,const char *,pathname,
  229. char *,buf,size_t,bufsize)
  230. #endif
  231. #if defined(TARGET_NR_renameat) && defined(__NR_renameat)
  232. _syscall4(int,sys_renameat,int,olddirfd,const char *,oldpath,
  233. int,newdirfd,const char *,newpath)
  234. #endif
  235. _syscall3(int,sys_rt_sigqueueinfo,int,pid,int,sig,siginfo_t *,uinfo)
  236. #if defined(TARGET_NR_symlinkat) && defined(__NR_symlinkat)
  237. _syscall3(int,sys_symlinkat,const char *,oldpath,
  238. int,newdirfd,const char *,newpath)
  239. #endif
  240. _syscall3(int,sys_syslog,int,type,char*,bufp,int,len)
  241. #if defined(TARGET_NR_tgkill) && defined(__NR_tgkill)
  242. _syscall3(int,sys_tgkill,int,tgid,int,pid,int,sig)
  243. #endif
  244. #if defined(TARGET_NR_tkill) && defined(__NR_tkill)
  245. _syscall2(int,sys_tkill,int,tid,int,sig)
  246. #endif
  247. #ifdef __NR_exit_group
  248. _syscall1(int,exit_group,int,error_code)
  249. #endif
  250. #if defined(TARGET_NR_set_tid_address) && defined(__NR_set_tid_address)
  251. _syscall1(int,set_tid_address,int *,tidptr)
  252. #endif
  253. #if defined(TARGET_NR_unlinkat) && defined(__NR_unlinkat)
  254. _syscall3(int,sys_unlinkat,int,dirfd,const char *,pathname,int,flags)
  255. #endif
  256. #if defined(TARGET_NR_utimensat) && defined(__NR_utimensat)
  257. _syscall4(int,sys_utimensat,int,dirfd,const char *,pathname,
  258. const struct timespec *,tsp,int,flags)
  259. #endif
  260. #if defined(TARGET_NR_inotify_init) && defined(__NR_inotify_init)
  261. _syscall0(int,sys_inotify_init)
  262. #endif
  263. #if defined(TARGET_NR_inotify_add_watch) && defined(__NR_inotify_add_watch)
  264. _syscall3(int,sys_inotify_add_watch,int,fd,const char *,pathname,uint32_t,mask)
  265. #endif
  266. #if defined(TARGET_NR_inotify_rm_watch) && defined(__NR_inotify_rm_watch)
  267. _syscall2(int,sys_inotify_rm_watch,int,fd,uint32_t,wd)
  268. #endif
  269. #if defined(USE_NPTL)
  270. #if defined(TARGET_NR_futex) && defined(__NR_futex)
  271. _syscall6(int,sys_futex,int *,uaddr,int,op,int,val,
  272. const struct timespec *,timeout,int *,uaddr2,int,val3)
  273. #endif
  274. #endif
  275. extern int personality(int);
  276. extern int flock(int, int);
  277. extern int setfsuid(int);
  278. extern int setfsgid(int);
  279. extern int setgroups(int, gid_t *);
  280. #define ERRNO_TABLE_SIZE 1200
  281. /* target_to_host_errno_table[] is initialized from
  282. * host_to_target_errno_table[] in syscall_init(). */
  283. static uint16_t target_to_host_errno_table[ERRNO_TABLE_SIZE] = {
  284. };
  285. /*
  286. * This list is the union of errno values overridden in asm-<arch>/errno.h
  287. * minus the errnos that are not actually generic to all archs.
  288. */
  289. static uint16_t host_to_target_errno_table[ERRNO_TABLE_SIZE] = {
  290. [EIDRM] = TARGET_EIDRM,
  291. [ECHRNG] = TARGET_ECHRNG,
  292. [EL2NSYNC] = TARGET_EL2NSYNC,
  293. [EL3HLT] = TARGET_EL3HLT,
  294. [EL3RST] = TARGET_EL3RST,
  295. [ELNRNG] = TARGET_ELNRNG,
  296. [EUNATCH] = TARGET_EUNATCH,
  297. [ENOCSI] = TARGET_ENOCSI,
  298. [EL2HLT] = TARGET_EL2HLT,
  299. [EDEADLK] = TARGET_EDEADLK,
  300. [ENOLCK] = TARGET_ENOLCK,
  301. [EBADE] = TARGET_EBADE,
  302. [EBADR] = TARGET_EBADR,
  303. [EXFULL] = TARGET_EXFULL,
  304. [ENOANO] = TARGET_ENOANO,
  305. [EBADRQC] = TARGET_EBADRQC,
  306. [EBADSLT] = TARGET_EBADSLT,
  307. [EBFONT] = TARGET_EBFONT,
  308. [ENOSTR] = TARGET_ENOSTR,
  309. [ENODATA] = TARGET_ENODATA,
  310. [ETIME] = TARGET_ETIME,
  311. [ENOSR] = TARGET_ENOSR,
  312. [ENONET] = TARGET_ENONET,
  313. [ENOPKG] = TARGET_ENOPKG,
  314. [EREMOTE] = TARGET_EREMOTE,
  315. [ENOLINK] = TARGET_ENOLINK,
  316. [EADV] = TARGET_EADV,
  317. [ESRMNT] = TARGET_ESRMNT,
  318. [ECOMM] = TARGET_ECOMM,
  319. [EPROTO] = TARGET_EPROTO,
  320. [EDOTDOT] = TARGET_EDOTDOT,
  321. [EMULTIHOP] = TARGET_EMULTIHOP,
  322. [EBADMSG] = TARGET_EBADMSG,
  323. [ENAMETOOLONG] = TARGET_ENAMETOOLONG,
  324. [EOVERFLOW] = TARGET_EOVERFLOW,
  325. [ENOTUNIQ] = TARGET_ENOTUNIQ,
  326. [EBADFD] = TARGET_EBADFD,
  327. [EREMCHG] = TARGET_EREMCHG,
  328. [ELIBACC] = TARGET_ELIBACC,
  329. [ELIBBAD] = TARGET_ELIBBAD,
  330. [ELIBSCN] = TARGET_ELIBSCN,
  331. [ELIBMAX] = TARGET_ELIBMAX,
  332. [ELIBEXEC] = TARGET_ELIBEXEC,
  333. [EILSEQ] = TARGET_EILSEQ,
  334. [ENOSYS] = TARGET_ENOSYS,
  335. [ELOOP] = TARGET_ELOOP,
  336. [ERESTART] = TARGET_ERESTART,
  337. [ESTRPIPE] = TARGET_ESTRPIPE,
  338. [ENOTEMPTY] = TARGET_ENOTEMPTY,
  339. [EUSERS] = TARGET_EUSERS,
  340. [ENOTSOCK] = TARGET_ENOTSOCK,
  341. [EDESTADDRREQ] = TARGET_EDESTADDRREQ,
  342. [EMSGSIZE] = TARGET_EMSGSIZE,
  343. [EPROTOTYPE] = TARGET_EPROTOTYPE,
  344. [ENOPROTOOPT] = TARGET_ENOPROTOOPT,
  345. [EPROTONOSUPPORT] = TARGET_EPROTONOSUPPORT,
  346. [ESOCKTNOSUPPORT] = TARGET_ESOCKTNOSUPPORT,
  347. [EOPNOTSUPP] = TARGET_EOPNOTSUPP,
  348. [EPFNOSUPPORT] = TARGET_EPFNOSUPPORT,
  349. [EAFNOSUPPORT] = TARGET_EAFNOSUPPORT,
  350. [EADDRINUSE] = TARGET_EADDRINUSE,
  351. [EADDRNOTAVAIL] = TARGET_EADDRNOTAVAIL,
  352. [ENETDOWN] = TARGET_ENETDOWN,
  353. [ENETUNREACH] = TARGET_ENETUNREACH,
  354. [ENETRESET] = TARGET_ENETRESET,
  355. [ECONNABORTED] = TARGET_ECONNABORTED,
  356. [ECONNRESET] = TARGET_ECONNRESET,
  357. [ENOBUFS] = TARGET_ENOBUFS,
  358. [EISCONN] = TARGET_EISCONN,
  359. [ENOTCONN] = TARGET_ENOTCONN,
  360. [EUCLEAN] = TARGET_EUCLEAN,
  361. [ENOTNAM] = TARGET_ENOTNAM,
  362. [ENAVAIL] = TARGET_ENAVAIL,
  363. [EISNAM] = TARGET_EISNAM,
  364. [EREMOTEIO] = TARGET_EREMOTEIO,
  365. [ESHUTDOWN] = TARGET_ESHUTDOWN,
  366. [ETOOMANYREFS] = TARGET_ETOOMANYREFS,
  367. [ETIMEDOUT] = TARGET_ETIMEDOUT,
  368. [ECONNREFUSED] = TARGET_ECONNREFUSED,
  369. [EHOSTDOWN] = TARGET_EHOSTDOWN,
  370. [EHOSTUNREACH] = TARGET_EHOSTUNREACH,
  371. [EALREADY] = TARGET_EALREADY,
  372. [EINPROGRESS] = TARGET_EINPROGRESS,
  373. [ESTALE] = TARGET_ESTALE,
  374. [ECANCELED] = TARGET_ECANCELED,
  375. [ENOMEDIUM] = TARGET_ENOMEDIUM,
  376. [EMEDIUMTYPE] = TARGET_EMEDIUMTYPE,
  377. #ifdef ENOKEY
  378. [ENOKEY] = TARGET_ENOKEY,
  379. #endif
  380. #ifdef EKEYEXPIRED
  381. [EKEYEXPIRED] = TARGET_EKEYEXPIRED,
  382. #endif
  383. #ifdef EKEYREVOKED
  384. [EKEYREVOKED] = TARGET_EKEYREVOKED,
  385. #endif
  386. #ifdef EKEYREJECTED
  387. [EKEYREJECTED] = TARGET_EKEYREJECTED,
  388. #endif
  389. #ifdef EOWNERDEAD
  390. [EOWNERDEAD] = TARGET_EOWNERDEAD,
  391. #endif
  392. #ifdef ENOTRECOVERABLE
  393. [ENOTRECOVERABLE] = TARGET_ENOTRECOVERABLE,
  394. #endif
  395. };
  396. static inline int host_to_target_errno(int err)
  397. {
  398. if(host_to_target_errno_table[err])
  399. return host_to_target_errno_table[err];
  400. return err;
  401. }
  402. static inline int target_to_host_errno(int err)
  403. {
  404. if (target_to_host_errno_table[err])
  405. return target_to_host_errno_table[err];
  406. return err;
  407. }
  408. static inline abi_long get_errno(abi_long ret)
  409. {
  410. if (ret == -1)
  411. return -host_to_target_errno(errno);
  412. else
  413. return ret;
  414. }
  415. static inline int is_error(abi_long ret)
  416. {
  417. return (abi_ulong)ret >= (abi_ulong)(-4096);
  418. }
  419. char *target_strerror(int err)
  420. {
  421. return strerror(target_to_host_errno(err));
  422. }
  423. static abi_ulong target_brk;
  424. static abi_ulong target_original_brk;
  425. void target_set_brk(abi_ulong new_brk)
  426. {
  427. target_original_brk = target_brk = HOST_PAGE_ALIGN(new_brk);
  428. }
  429. /* do_brk() must return target values and target errnos. */
  430. abi_long do_brk(abi_ulong new_brk)
  431. {
  432. abi_ulong brk_page;
  433. abi_long mapped_addr;
  434. int new_alloc_size;
  435. if (!new_brk)
  436. return target_brk;
  437. if (new_brk < target_original_brk)
  438. return target_brk;
  439. brk_page = HOST_PAGE_ALIGN(target_brk);
  440. /* If the new brk is less than this, set it and we're done... */
  441. if (new_brk < brk_page) {
  442. target_brk = new_brk;
  443. return target_brk;
  444. }
  445. /* We need to allocate more memory after the brk... */
  446. new_alloc_size = HOST_PAGE_ALIGN(new_brk - brk_page + 1);
  447. mapped_addr = get_errno(target_mmap(brk_page, new_alloc_size,
  448. PROT_READ|PROT_WRITE,
  449. MAP_ANON|MAP_FIXED|MAP_PRIVATE, 0, 0));
  450. if (!is_error(mapped_addr))
  451. target_brk = new_brk;
  452. return target_brk;
  453. }
  454. static inline abi_long copy_from_user_fdset(fd_set *fds,
  455. abi_ulong target_fds_addr,
  456. int n)
  457. {
  458. int i, nw, j, k;
  459. abi_ulong b, *target_fds;
  460. nw = (n + TARGET_ABI_BITS - 1) / TARGET_ABI_BITS;
  461. if (!(target_fds = lock_user(VERIFY_READ,
  462. target_fds_addr,
  463. sizeof(abi_ulong) * nw,
  464. 1)))
  465. return -TARGET_EFAULT;
  466. FD_ZERO(fds);
  467. k = 0;
  468. for (i = 0; i < nw; i++) {
  469. /* grab the abi_ulong */
  470. __get_user(b, &target_fds[i]);
  471. for (j = 0; j < TARGET_ABI_BITS; j++) {
  472. /* check the bit inside the abi_ulong */
  473. if ((b >> j) & 1)
  474. FD_SET(k, fds);
  475. k++;
  476. }
  477. }
  478. unlock_user(target_fds, target_fds_addr, 0);
  479. return 0;
  480. }
  481. static inline abi_long copy_to_user_fdset(abi_ulong target_fds_addr,
  482. const fd_set *fds,
  483. int n)
  484. {
  485. int i, nw, j, k;
  486. abi_long v;
  487. abi_ulong *target_fds;
  488. nw = (n + TARGET_ABI_BITS - 1) / TARGET_ABI_BITS;
  489. if (!(target_fds = lock_user(VERIFY_WRITE,
  490. target_fds_addr,
  491. sizeof(abi_ulong) * nw,
  492. 0)))
  493. return -TARGET_EFAULT;
  494. k = 0;
  495. for (i = 0; i < nw; i++) {
  496. v = 0;
  497. for (j = 0; j < TARGET_ABI_BITS; j++) {
  498. v |= ((FD_ISSET(k, fds) != 0) << j);
  499. k++;
  500. }
  501. __put_user(v, &target_fds[i]);
  502. }
  503. unlock_user(target_fds, target_fds_addr, sizeof(abi_ulong) * nw);
  504. return 0;
  505. }
  506. #if defined(__alpha__)
  507. #define HOST_HZ 1024
  508. #else
  509. #define HOST_HZ 100
  510. #endif
  511. static inline abi_long host_to_target_clock_t(long ticks)
  512. {
  513. #if HOST_HZ == TARGET_HZ
  514. return ticks;
  515. #else
  516. return ((int64_t)ticks * TARGET_HZ) / HOST_HZ;
  517. #endif
  518. }
  519. static inline abi_long host_to_target_rusage(abi_ulong target_addr,
  520. const struct rusage *rusage)
  521. {
  522. struct target_rusage *target_rusage;
  523. if (!lock_user_struct(VERIFY_WRITE, target_rusage, target_addr, 0))
  524. return -TARGET_EFAULT;
  525. target_rusage->ru_utime.tv_sec = tswapl(rusage->ru_utime.tv_sec);
  526. target_rusage->ru_utime.tv_usec = tswapl(rusage->ru_utime.tv_usec);
  527. target_rusage->ru_stime.tv_sec = tswapl(rusage->ru_stime.tv_sec);
  528. target_rusage->ru_stime.tv_usec = tswapl(rusage->ru_stime.tv_usec);
  529. target_rusage->ru_maxrss = tswapl(rusage->ru_maxrss);
  530. target_rusage->ru_ixrss = tswapl(rusage->ru_ixrss);
  531. target_rusage->ru_idrss = tswapl(rusage->ru_idrss);
  532. target_rusage->ru_isrss = tswapl(rusage->ru_isrss);
  533. target_rusage->ru_minflt = tswapl(rusage->ru_minflt);
  534. target_rusage->ru_majflt = tswapl(rusage->ru_majflt);
  535. target_rusage->ru_nswap = tswapl(rusage->ru_nswap);
  536. target_rusage->ru_inblock = tswapl(rusage->ru_inblock);
  537. target_rusage->ru_oublock = tswapl(rusage->ru_oublock);
  538. target_rusage->ru_msgsnd = tswapl(rusage->ru_msgsnd);
  539. target_rusage->ru_msgrcv = tswapl(rusage->ru_msgrcv);
  540. target_rusage->ru_nsignals = tswapl(rusage->ru_nsignals);
  541. target_rusage->ru_nvcsw = tswapl(rusage->ru_nvcsw);
  542. target_rusage->ru_nivcsw = tswapl(rusage->ru_nivcsw);
  543. unlock_user_struct(target_rusage, target_addr, 1);
  544. return 0;
  545. }
  546. static inline abi_long copy_from_user_timeval(struct timeval *tv,
  547. abi_ulong target_tv_addr)
  548. {
  549. struct target_timeval *target_tv;
  550. if (!lock_user_struct(VERIFY_READ, target_tv, target_tv_addr, 1))
  551. return -TARGET_EFAULT;
  552. __get_user(tv->tv_sec, &target_tv->tv_sec);
  553. __get_user(tv->tv_usec, &target_tv->tv_usec);
  554. unlock_user_struct(target_tv, target_tv_addr, 0);
  555. return 0;
  556. }
  557. static inline abi_long copy_to_user_timeval(abi_ulong target_tv_addr,
  558. const struct timeval *tv)
  559. {
  560. struct target_timeval *target_tv;
  561. if (!lock_user_struct(VERIFY_WRITE, target_tv, target_tv_addr, 0))
  562. return -TARGET_EFAULT;
  563. __put_user(tv->tv_sec, &target_tv->tv_sec);
  564. __put_user(tv->tv_usec, &target_tv->tv_usec);
  565. unlock_user_struct(target_tv, target_tv_addr, 1);
  566. return 0;
  567. }
  568. /* do_select() must return target values and target errnos. */
  569. static abi_long do_select(int n,
  570. abi_ulong rfd_addr, abi_ulong wfd_addr,
  571. abi_ulong efd_addr, abi_ulong target_tv_addr)
  572. {
  573. fd_set rfds, wfds, efds;
  574. fd_set *rfds_ptr, *wfds_ptr, *efds_ptr;
  575. struct timeval tv, *tv_ptr;
  576. abi_long ret;
  577. if (rfd_addr) {
  578. if (copy_from_user_fdset(&rfds, rfd_addr, n))
  579. return -TARGET_EFAULT;
  580. rfds_ptr = &rfds;
  581. } else {
  582. rfds_ptr = NULL;
  583. }
  584. if (wfd_addr) {
  585. if (copy_from_user_fdset(&wfds, wfd_addr, n))
  586. return -TARGET_EFAULT;
  587. wfds_ptr = &wfds;
  588. } else {
  589. wfds_ptr = NULL;
  590. }
  591. if (efd_addr) {
  592. if (copy_from_user_fdset(&efds, efd_addr, n))
  593. return -TARGET_EFAULT;
  594. efds_ptr = &efds;
  595. } else {
  596. efds_ptr = NULL;
  597. }
  598. if (target_tv_addr) {
  599. if (copy_from_user_timeval(&tv, target_tv_addr))
  600. return -TARGET_EFAULT;
  601. tv_ptr = &tv;
  602. } else {
  603. tv_ptr = NULL;
  604. }
  605. ret = get_errno(select(n, rfds_ptr, wfds_ptr, efds_ptr, tv_ptr));
  606. if (!is_error(ret)) {
  607. if (rfd_addr && copy_to_user_fdset(rfd_addr, &rfds, n))
  608. return -TARGET_EFAULT;
  609. if (wfd_addr && copy_to_user_fdset(wfd_addr, &wfds, n))
  610. return -TARGET_EFAULT;
  611. if (efd_addr && copy_to_user_fdset(efd_addr, &efds, n))
  612. return -TARGET_EFAULT;
  613. if (target_tv_addr && copy_to_user_timeval(target_tv_addr, &tv))
  614. return -TARGET_EFAULT;
  615. }
  616. return ret;
  617. }
  618. static inline abi_long target_to_host_sockaddr(struct sockaddr *addr,
  619. abi_ulong target_addr,
  620. socklen_t len)
  621. {
  622. struct target_sockaddr *target_saddr;
  623. target_saddr = lock_user(VERIFY_READ, target_addr, len, 1);
  624. if (!target_saddr)
  625. return -TARGET_EFAULT;
  626. memcpy(addr, target_saddr, len);
  627. addr->sa_family = tswap16(target_saddr->sa_family);
  628. unlock_user(target_saddr, target_addr, 0);
  629. return 0;
  630. }
  631. static inline abi_long host_to_target_sockaddr(abi_ulong target_addr,
  632. struct sockaddr *addr,
  633. socklen_t len)
  634. {
  635. struct target_sockaddr *target_saddr;
  636. target_saddr = lock_user(VERIFY_WRITE, target_addr, len, 0);
  637. if (!target_saddr)
  638. return -TARGET_EFAULT;
  639. memcpy(target_saddr, addr, len);
  640. target_saddr->sa_family = tswap16(addr->sa_family);
  641. unlock_user(target_saddr, target_addr, len);
  642. return 0;
  643. }
  644. /* ??? Should this also swap msgh->name? */
  645. static inline abi_long target_to_host_cmsg(struct msghdr *msgh,
  646. struct target_msghdr *target_msgh)
  647. {
  648. struct cmsghdr *cmsg = CMSG_FIRSTHDR(msgh);
  649. abi_long msg_controllen;
  650. abi_ulong target_cmsg_addr;
  651. struct target_cmsghdr *target_cmsg;
  652. socklen_t space = 0;
  653. msg_controllen = tswapl(target_msgh->msg_controllen);
  654. if (msg_controllen < sizeof (struct target_cmsghdr))
  655. goto the_end;
  656. target_cmsg_addr = tswapl(target_msgh->msg_control);
  657. target_cmsg = lock_user(VERIFY_READ, target_cmsg_addr, msg_controllen, 1);
  658. if (!target_cmsg)
  659. return -TARGET_EFAULT;
  660. while (cmsg && target_cmsg) {
  661. void *data = CMSG_DATA(cmsg);
  662. void *target_data = TARGET_CMSG_DATA(target_cmsg);
  663. int len = tswapl(target_cmsg->cmsg_len)
  664. - TARGET_CMSG_ALIGN(sizeof (struct target_cmsghdr));
  665. space += CMSG_SPACE(len);
  666. if (space > msgh->msg_controllen) {
  667. space -= CMSG_SPACE(len);
  668. gemu_log("Host cmsg overflow\n");
  669. break;
  670. }
  671. cmsg->cmsg_level = tswap32(target_cmsg->cmsg_level);
  672. cmsg->cmsg_type = tswap32(target_cmsg->cmsg_type);
  673. cmsg->cmsg_len = CMSG_LEN(len);
  674. if (cmsg->cmsg_level != TARGET_SOL_SOCKET || cmsg->cmsg_type != SCM_RIGHTS) {
  675. gemu_log("Unsupported ancillary data: %d/%d\n", cmsg->cmsg_level, cmsg->cmsg_type);
  676. memcpy(data, target_data, len);
  677. } else {
  678. int *fd = (int *)data;
  679. int *target_fd = (int *)target_data;
  680. int i, numfds = len / sizeof(int);
  681. for (i = 0; i < numfds; i++)
  682. fd[i] = tswap32(target_fd[i]);
  683. }
  684. cmsg = CMSG_NXTHDR(msgh, cmsg);
  685. target_cmsg = TARGET_CMSG_NXTHDR(target_msgh, target_cmsg);
  686. }
  687. unlock_user(target_cmsg, target_cmsg_addr, 0);
  688. the_end:
  689. msgh->msg_controllen = space;
  690. return 0;
  691. }
  692. /* ??? Should this also swap msgh->name? */
  693. static inline abi_long host_to_target_cmsg(struct target_msghdr *target_msgh,
  694. struct msghdr *msgh)
  695. {
  696. struct cmsghdr *cmsg = CMSG_FIRSTHDR(msgh);
  697. abi_long msg_controllen;
  698. abi_ulong target_cmsg_addr;
  699. struct target_cmsghdr *target_cmsg;
  700. socklen_t space = 0;
  701. msg_controllen = tswapl(target_msgh->msg_controllen);
  702. if (msg_controllen < sizeof (struct target_cmsghdr))
  703. goto the_end;
  704. target_cmsg_addr = tswapl(target_msgh->msg_control);
  705. target_cmsg = lock_user(VERIFY_WRITE, target_cmsg_addr, msg_controllen, 0);
  706. if (!target_cmsg)
  707. return -TARGET_EFAULT;
  708. while (cmsg && target_cmsg) {
  709. void *data = CMSG_DATA(cmsg);
  710. void *target_data = TARGET_CMSG_DATA(target_cmsg);
  711. int len = cmsg->cmsg_len - CMSG_ALIGN(sizeof (struct cmsghdr));
  712. space += TARGET_CMSG_SPACE(len);
  713. if (space > msg_controllen) {
  714. space -= TARGET_CMSG_SPACE(len);
  715. gemu_log("Target cmsg overflow\n");
  716. break;
  717. }
  718. target_cmsg->cmsg_level = tswap32(cmsg->cmsg_level);
  719. target_cmsg->cmsg_type = tswap32(cmsg->cmsg_type);
  720. target_cmsg->cmsg_len = tswapl(TARGET_CMSG_LEN(len));
  721. if (cmsg->cmsg_level != TARGET_SOL_SOCKET || cmsg->cmsg_type != SCM_RIGHTS) {
  722. gemu_log("Unsupported ancillary data: %d/%d\n", cmsg->cmsg_level, cmsg->cmsg_type);
  723. memcpy(target_data, data, len);
  724. } else {
  725. int *fd = (int *)data;
  726. int *target_fd = (int *)target_data;
  727. int i, numfds = len / sizeof(int);
  728. for (i = 0; i < numfds; i++)
  729. target_fd[i] = tswap32(fd[i]);
  730. }
  731. cmsg = CMSG_NXTHDR(msgh, cmsg);
  732. target_cmsg = TARGET_CMSG_NXTHDR(target_msgh, target_cmsg);
  733. }
  734. unlock_user(target_cmsg, target_cmsg_addr, space);
  735. the_end:
  736. target_msgh->msg_controllen = tswapl(space);
  737. return 0;
  738. }
  739. /* do_setsockopt() Must return target values and target errnos. */
  740. static abi_long do_setsockopt(int sockfd, int level, int optname,
  741. abi_ulong optval_addr, socklen_t optlen)
  742. {
  743. abi_long ret;
  744. int val;
  745. switch(level) {
  746. case SOL_TCP:
  747. /* TCP options all take an 'int' value. */
  748. if (optlen < sizeof(uint32_t))
  749. return -TARGET_EINVAL;
  750. if (get_user_u32(val, optval_addr))
  751. return -TARGET_EFAULT;
  752. ret = get_errno(setsockopt(sockfd, level, optname, &val, sizeof(val)));
  753. break;
  754. case SOL_IP:
  755. switch(optname) {
  756. case IP_TOS:
  757. case IP_TTL:
  758. case IP_HDRINCL:
  759. case IP_ROUTER_ALERT:
  760. case IP_RECVOPTS:
  761. case IP_RETOPTS:
  762. case IP_PKTINFO:
  763. case IP_MTU_DISCOVER:
  764. case IP_RECVERR:
  765. case IP_RECVTOS:
  766. #ifdef IP_FREEBIND
  767. case IP_FREEBIND:
  768. #endif
  769. case IP_MULTICAST_TTL:
  770. case IP_MULTICAST_LOOP:
  771. val = 0;
  772. if (optlen >= sizeof(uint32_t)) {
  773. if (get_user_u32(val, optval_addr))
  774. return -TARGET_EFAULT;
  775. } else if (optlen >= 1) {
  776. if (get_user_u8(val, optval_addr))
  777. return -TARGET_EFAULT;
  778. }
  779. ret = get_errno(setsockopt(sockfd, level, optname, &val, sizeof(val)));
  780. break;
  781. default:
  782. goto unimplemented;
  783. }
  784. break;
  785. case TARGET_SOL_SOCKET:
  786. switch (optname) {
  787. /* Options with 'int' argument. */
  788. case TARGET_SO_DEBUG:
  789. optname = SO_DEBUG;
  790. break;
  791. case TARGET_SO_REUSEADDR:
  792. optname = SO_REUSEADDR;
  793. break;
  794. case TARGET_SO_TYPE:
  795. optname = SO_TYPE;
  796. break;
  797. case TARGET_SO_ERROR:
  798. optname = SO_ERROR;
  799. break;
  800. case TARGET_SO_DONTROUTE:
  801. optname = SO_DONTROUTE;
  802. break;
  803. case TARGET_SO_BROADCAST:
  804. optname = SO_BROADCAST;
  805. break;
  806. case TARGET_SO_SNDBUF:
  807. optname = SO_SNDBUF;
  808. break;
  809. case TARGET_SO_RCVBUF:
  810. optname = SO_RCVBUF;
  811. break;
  812. case TARGET_SO_KEEPALIVE:
  813. optname = SO_KEEPALIVE;
  814. break;
  815. case TARGET_SO_OOBINLINE:
  816. optname = SO_OOBINLINE;
  817. break;
  818. case TARGET_SO_NO_CHECK:
  819. optname = SO_NO_CHECK;
  820. break;
  821. case TARGET_SO_PRIORITY:
  822. optname = SO_PRIORITY;
  823. break;
  824. #ifdef SO_BSDCOMPAT
  825. case TARGET_SO_BSDCOMPAT:
  826. optname = SO_BSDCOMPAT;
  827. break;
  828. #endif
  829. case TARGET_SO_PASSCRED:
  830. optname = SO_PASSCRED;
  831. break;
  832. case TARGET_SO_TIMESTAMP:
  833. optname = SO_TIMESTAMP;
  834. break;
  835. case TARGET_SO_RCVLOWAT:
  836. optname = SO_RCVLOWAT;
  837. break;
  838. case TARGET_SO_RCVTIMEO:
  839. optname = SO_RCVTIMEO;
  840. break;
  841. case TARGET_SO_SNDTIMEO:
  842. optname = SO_SNDTIMEO;
  843. break;
  844. break;
  845. default:
  846. goto unimplemented;
  847. }
  848. if (optlen < sizeof(uint32_t))
  849. return -TARGET_EINVAL;
  850. if (get_user_u32(val, optval_addr))
  851. return -TARGET_EFAULT;
  852. ret = get_errno(setsockopt(sockfd, SOL_SOCKET, optname, &val, sizeof(val)));
  853. break;
  854. default:
  855. unimplemented:
  856. gemu_log("Unsupported setsockopt level=%d optname=%d \n", level, optname);
  857. ret = -TARGET_ENOPROTOOPT;
  858. }
  859. return ret;
  860. }
  861. /* do_getsockopt() Must return target values and target errnos. */
  862. static abi_long do_getsockopt(int sockfd, int level, int optname,
  863. abi_ulong optval_addr, abi_ulong optlen)
  864. {
  865. abi_long ret;
  866. int len, val;
  867. socklen_t lv;
  868. switch(level) {
  869. case TARGET_SOL_SOCKET:
  870. level = SOL_SOCKET;
  871. switch (optname) {
  872. case TARGET_SO_LINGER:
  873. case TARGET_SO_RCVTIMEO:
  874. case TARGET_SO_SNDTIMEO:
  875. case TARGET_SO_PEERCRED:
  876. case TARGET_SO_PEERNAME:
  877. /* These don't just return a single integer */
  878. goto unimplemented;
  879. default:
  880. goto int_case;
  881. }
  882. break;
  883. case SOL_TCP:
  884. /* TCP options all take an 'int' value. */
  885. int_case:
  886. if (get_user_u32(len, optlen))
  887. return -TARGET_EFAULT;
  888. if (len < 0)
  889. return -TARGET_EINVAL;
  890. lv = sizeof(int);
  891. ret = get_errno(getsockopt(sockfd, level, optname, &val, &lv));
  892. if (ret < 0)
  893. return ret;
  894. val = tswap32(val);
  895. if (len > lv)
  896. len = lv;
  897. if (len == 4) {
  898. if (put_user_u32(val, optval_addr))
  899. return -TARGET_EFAULT;
  900. } else {
  901. if (put_user_u8(val, optval_addr))
  902. return -TARGET_EFAULT;
  903. }
  904. if (put_user_u32(len, optlen))
  905. return -TARGET_EFAULT;
  906. break;
  907. case SOL_IP:
  908. switch(optname) {
  909. case IP_TOS:
  910. case IP_TTL:
  911. case IP_HDRINCL:
  912. case IP_ROUTER_ALERT:
  913. case IP_RECVOPTS:
  914. case IP_RETOPTS:
  915. case IP_PKTINFO:
  916. case IP_MTU_DISCOVER:
  917. case IP_RECVERR:
  918. case IP_RECVTOS:
  919. #ifdef IP_FREEBIND
  920. case IP_FREEBIND:
  921. #endif
  922. case IP_MULTICAST_TTL:
  923. case IP_MULTICAST_LOOP:
  924. if (get_user_u32(len, optlen))
  925. return -TARGET_EFAULT;
  926. if (len < 0)
  927. return -TARGET_EINVAL;
  928. lv = sizeof(int);
  929. ret = get_errno(getsockopt(sockfd, level, optname, &val, &lv));
  930. if (ret < 0)
  931. return ret;
  932. if (len < sizeof(int) && len > 0 && val >= 0 && val < 255) {
  933. len = 1;
  934. if (put_user_u32(len, optlen)
  935. || put_user_u8(val, optval_addr))
  936. return -TARGET_EFAULT;
  937. } else {
  938. if (len > sizeof(int))
  939. len = sizeof(int);
  940. if (put_user_u32(len, optlen)
  941. || put_user_u32(val, optval_addr))
  942. return -TARGET_EFAULT;
  943. }
  944. break;
  945. default:
  946. ret = -TARGET_ENOPROTOOPT;
  947. break;
  948. }
  949. break;
  950. default:
  951. unimplemented:
  952. gemu_log("getsockopt level=%d optname=%d not yet supported\n",
  953. level, optname);
  954. ret = -TARGET_EOPNOTSUPP;
  955. break;
  956. }
  957. return ret;
  958. }
  959. /* FIXME
  960. * lock_iovec()/unlock_iovec() have a return code of 0 for success where
  961. * other lock functions have a return code of 0 for failure.
  962. */
  963. static abi_long lock_iovec(int type, struct iovec *vec, abi_ulong target_addr,
  964. int count, int copy)
  965. {
  966. struct target_iovec *target_vec;
  967. abi_ulong base;
  968. int i;
  969. target_vec = lock_user(VERIFY_READ, target_addr, count * sizeof(struct target_iovec), 1);
  970. if (!target_vec)
  971. return -TARGET_EFAULT;
  972. for(i = 0;i < count; i++) {
  973. base = tswapl(target_vec[i].iov_base);
  974. vec[i].iov_len = tswapl(target_vec[i].iov_len);
  975. if (vec[i].iov_len != 0) {
  976. vec[i].iov_base = lock_user(type, base, vec[i].iov_len, copy);
  977. /* Don't check lock_user return value. We must call writev even
  978. if a element has invalid base address. */
  979. } else {
  980. /* zero length pointer is ignored */
  981. vec[i].iov_base = NULL;
  982. }
  983. }
  984. unlock_user (target_vec, target_addr, 0);
  985. return 0;
  986. }
  987. static abi_long unlock_iovec(struct iovec *vec, abi_ulong target_addr,
  988. int count, int copy)
  989. {
  990. struct target_iovec *target_vec;
  991. abi_ulong base;
  992. int i;
  993. target_vec = lock_user(VERIFY_READ, target_addr, count * sizeof(struct target_iovec), 1);
  994. if (!target_vec)
  995. return -TARGET_EFAULT;
  996. for(i = 0;i < count; i++) {
  997. if (target_vec[i].iov_base) {
  998. base = tswapl(target_vec[i].iov_base);
  999. unlock_user(vec[i].iov_base, base, copy ? vec[i].iov_len : 0);
  1000. }
  1001. }
  1002. unlock_user (target_vec, target_addr, 0);
  1003. return 0;
  1004. }
  1005. /* do_socket() Must return target values and target errnos. */
  1006. static abi_long do_socket(int domain, int type, int protocol)
  1007. {
  1008. #if defined(TARGET_MIPS)
  1009. switch(type) {
  1010. case TARGET_SOCK_DGRAM:
  1011. type = SOCK_DGRAM;
  1012. break;
  1013. case TARGET_SOCK_STREAM:
  1014. type = SOCK_STREAM;
  1015. break;
  1016. case TARGET_SOCK_RAW:
  1017. type = SOCK_RAW;
  1018. break;
  1019. case TARGET_SOCK_RDM:
  1020. type = SOCK_RDM;
  1021. break;
  1022. case TARGET_SOCK_SEQPACKET:
  1023. type = SOCK_SEQPACKET;
  1024. break;
  1025. case TARGET_SOCK_PACKET:
  1026. type = SOCK_PACKET;
  1027. break;
  1028. }
  1029. #endif
  1030. if (domain == PF_NETLINK)
  1031. return -EAFNOSUPPORT; /* do not NETLINK socket connections possible */
  1032. return get_errno(socket(domain, type, protocol));
  1033. }
  1034. /* MAX_SOCK_ADDR from linux/net/socket.c */
  1035. #define MAX_SOCK_ADDR 128
  1036. /* do_bind() Must return target values and target errnos. */
  1037. static abi_long do_bind(int sockfd, abi_ulong target_addr,
  1038. socklen_t addrlen)
  1039. {
  1040. void *addr;
  1041. if (addrlen < 0 || addrlen > MAX_SOCK_ADDR)
  1042. return -TARGET_EINVAL;
  1043. addr = alloca(addrlen);
  1044. target_to_host_sockaddr(addr, target_addr, addrlen);
  1045. return get_errno(bind(sockfd, addr, addrlen));
  1046. }
  1047. /* do_connect() Must return target values and target errnos. */
  1048. static abi_long do_connect(int sockfd, abi_ulong target_addr,
  1049. socklen_t addrlen)
  1050. {
  1051. void *addr;
  1052. if (addrlen < 0 || addrlen > MAX_SOCK_ADDR)
  1053. return -TARGET_EINVAL;
  1054. addr = alloca(addrlen);
  1055. target_to_host_sockaddr(addr, target_addr, addrlen);
  1056. return get_errno(connect(sockfd, addr, addrlen));
  1057. }
  1058. /* do_sendrecvmsg() Must return target values and target errnos. */
  1059. static abi_long do_sendrecvmsg(int fd, abi_ulong target_msg,
  1060. int flags, int send)
  1061. {
  1062. abi_long ret, len;
  1063. struct target_msghdr *msgp;
  1064. struct msghdr msg;
  1065. int count;
  1066. struct iovec *vec;
  1067. abi_ulong target_vec;
  1068. /* FIXME */
  1069. if (!lock_user_struct(send ? VERIFY_READ : VERIFY_WRITE,
  1070. msgp,
  1071. target_msg,
  1072. send ? 1 : 0))
  1073. return -TARGET_EFAULT;
  1074. if (msgp->msg_name) {
  1075. msg.msg_namelen = tswap32(msgp->msg_namelen);
  1076. msg.msg_name = alloca(msg.msg_namelen);
  1077. target_to_host_sockaddr(msg.msg_name, tswapl(msgp->msg_name),
  1078. msg.msg_namelen);
  1079. } else {
  1080. msg.msg_name = NULL;
  1081. msg.msg_namelen = 0;
  1082. }
  1083. msg.msg_controllen = 2 * tswapl(msgp->msg_controllen);
  1084. msg.msg_control = alloca(msg.msg_controllen);
  1085. msg.msg_flags = tswap32(msgp->msg_flags);
  1086. count = tswapl(msgp->msg_iovlen);
  1087. vec = alloca(count * sizeof(struct iovec));
  1088. target_vec = tswapl(msgp->msg_iov);
  1089. lock_iovec(send ? VERIFY_READ : VERIFY_WRITE, vec, target_vec, count, send);
  1090. msg.msg_iovlen = count;
  1091. msg.msg_iov = vec;
  1092. if (send) {
  1093. ret = target_to_host_cmsg(&msg, msgp);
  1094. if (ret == 0)
  1095. ret = get_errno(sendmsg(fd, &msg, flags));
  1096. } else {
  1097. ret = get_errno(recvmsg(fd, &msg, flags));
  1098. if (!is_error(ret)) {
  1099. len = ret;
  1100. ret = host_to_target_cmsg(msgp, &msg);
  1101. if (!is_error(ret))
  1102. ret = len;
  1103. }
  1104. }
  1105. unlock_iovec(vec, target_vec, count, !send);
  1106. unlock_user_struct(msgp, target_msg, send ? 0 : 1);
  1107. return ret;
  1108. }
  1109. /* do_accept() Must return target values and target errnos. */
  1110. static abi_long do_accept(int fd, abi_ulong target_addr,
  1111. abi_ulong target_addrlen_addr)
  1112. {
  1113. socklen_t addrlen;
  1114. void *addr;
  1115. abi_long ret;
  1116. if (get_user_u32(addrlen, target_addrlen_addr))
  1117. return -TARGET_EFAULT;
  1118. if (addrlen < 0 || addrlen > MAX_SOCK_ADDR)
  1119. return -TARGET_EINVAL;
  1120. addr = alloca(addrlen);
  1121. ret = get_errno(accept(fd, addr, &addrlen));
  1122. if (!is_error(ret)) {
  1123. host_to_target_sockaddr(target_addr, addr, addrlen);
  1124. if (put_user_u32(addrlen, target_addrlen_addr))
  1125. ret = -TARGET_EFAULT;
  1126. }
  1127. return ret;
  1128. }
  1129. /* do_getpeername() Must return target values and target errnos. */
  1130. static abi_long do_getpeername(int fd, abi_ulong target_addr,
  1131. abi_ulong target_addrlen_addr)
  1132. {
  1133. socklen_t addrlen;
  1134. void *addr;
  1135. abi_long ret;
  1136. if (get_user_u32(addrlen, target_addrlen_addr))
  1137. return -TARGET_EFAULT;
  1138. if (addrlen < 0 || addrlen > MAX_SOCK_ADDR)
  1139. return -TARGET_EINVAL;
  1140. addr = alloca(addrlen);
  1141. ret = get_errno(getpeername(fd, addr, &addrlen));
  1142. if (!is_error(ret)) {
  1143. host_to_target_sockaddr(target_addr, addr, addrlen);
  1144. if (put_user_u32(addrlen, target_addrlen_addr))
  1145. ret = -TARGET_EFAULT;
  1146. }
  1147. return ret;
  1148. }
  1149. /* do_getsockname() Must return target values and target errnos. */
  1150. static abi_long do_getsockname(int fd, abi_ulong target_addr,
  1151. abi_ulong target_addrlen_addr)
  1152. {
  1153. socklen_t addrlen;
  1154. void *addr;
  1155. abi_long ret;
  1156. if (target_addr == 0)
  1157. return get_errno(accept(fd, NULL, NULL));
  1158. if (get_user_u32(addrlen, target_addrlen_addr))
  1159. return -TARGET_EFAULT;
  1160. if (addrlen < 0 || addrlen > MAX_SOCK_ADDR)
  1161. return -TARGET_EINVAL;
  1162. addr = alloca(addrlen);
  1163. ret = get_errno(getsockname(fd, addr, &addrlen));
  1164. if (!is_error(ret)) {
  1165. host_to_target_sockaddr(target_addr, addr, addrlen);
  1166. if (put_user_u32(addrlen, target_addrlen_addr))
  1167. ret = -TARGET_EFAULT;
  1168. }
  1169. return ret;
  1170. }
  1171. /* do_socketpair() Must return target values and target errnos. */
  1172. static abi_long do_socketpair(int domain, int type, int protocol,
  1173. abi_ulong target_tab_addr)
  1174. {
  1175. int tab[2];
  1176. abi_long ret;
  1177. ret = get_errno(socketpair(domain, type, protocol, tab));
  1178. if (!is_error(ret)) {
  1179. if (put_user_s32(tab[0], target_tab_addr)
  1180. || put_user_s32(tab[1], target_tab_addr + sizeof(tab[0])))
  1181. ret = -TARGET_EFAULT;
  1182. }
  1183. return ret;
  1184. }
  1185. /* do_sendto() Must return target values and target errnos. */
  1186. static abi_long do_sendto(int fd, abi_ulong msg, size_t len, int flags,
  1187. abi_ulong target_addr, socklen_t addrlen)
  1188. {
  1189. void *addr;
  1190. void *host_msg;
  1191. abi_long ret;
  1192. if (addrlen < 0 || addrlen > MAX_SOCK_ADDR)
  1193. return -TARGET_EINVAL;
  1194. host_msg = lock_user(VERIFY_READ, msg, len, 1);
  1195. if (!host_msg)
  1196. return -TARGET_EFAULT;
  1197. if (target_addr) {
  1198. addr = alloca(addrlen);
  1199. target_to_host_sockaddr(addr, target_addr, addrlen);
  1200. ret = get_errno(sendto(fd, host_msg, len, flags, addr, addrlen));
  1201. } else {
  1202. ret = get_errno(send(fd, host_msg, len, flags));
  1203. }
  1204. unlock_user(host_msg, msg, 0);
  1205. return ret;
  1206. }
  1207. /* do_recvfrom() Must return target values and target errnos. */
  1208. static abi_long do_recvfrom(int fd, abi_ulong msg, size_t len, int flags,
  1209. abi_ulong target_addr,
  1210. abi_ulong target_addrlen)
  1211. {
  1212. socklen_t addrlen;
  1213. void *addr;
  1214. void *host_msg;
  1215. abi_long ret;
  1216. host_msg = lock_user(VERIFY_WRITE, msg, len, 0);
  1217. if (!host_msg)
  1218. return -TARGET_EFAULT;
  1219. if (target_addr) {
  1220. if (get_user_u32(addrlen, target_addrlen)) {
  1221. ret = -TARGET_EFAULT;
  1222. goto fail;
  1223. }
  1224. if (addrlen < 0 || addrlen > MAX_SOCK_ADDR) {
  1225. ret = -TARGET_EINVAL;
  1226. goto fail;
  1227. }
  1228. addr = alloca(addrlen);
  1229. ret = get_errno(recvfrom(fd, host_msg, len, flags, addr, &addrlen));
  1230. } else {
  1231. addr = NULL; /* To keep compiler quiet. */
  1232. ret = get_errno(recv(fd, host_msg, len, flags));
  1233. }
  1234. if (!is_error(ret)) {
  1235. if (target_addr) {
  1236. host_to_target_sockaddr(target_addr, addr, addrlen);
  1237. if (put_user_u32(addrlen, target_addrlen)) {
  1238. ret = -TARGET_EFAULT;
  1239. goto fail;
  1240. }
  1241. }
  1242. unlock_user(host_msg, msg, len);
  1243. } else {
  1244. fail:
  1245. unlock_user(host_msg, msg, 0);
  1246. }
  1247. return ret;
  1248. }
  1249. #ifdef TARGET_NR_socketcall
  1250. /* do_socketcall() Must return target values and target errnos. */
  1251. static abi_long do_socketcall(int num, abi_ulong vptr)
  1252. {
  1253. abi_long ret;
  1254. const int n = sizeof(abi_ulong);
  1255. switch(num) {
  1256. case SOCKOP_socket:
  1257. {
  1258. int domain, type, protocol;
  1259. if (get_user_s32(domain, vptr)
  1260. || get_user_s32(type, vptr + n)
  1261. || get_user_s32(protocol, vptr + 2 * n))
  1262. return -TARGET_EFAULT;
  1263. ret = do_socket(domain, type, protocol);
  1264. }
  1265. break;
  1266. case SOCKOP_bind:
  1267. {
  1268. int sockfd;
  1269. abi_ulong target_addr;
  1270. socklen_t addrlen;
  1271. if (get_user_s32(sockfd, vptr)
  1272. || get_user_ual(target_addr, vptr + n)
  1273. || get_user_u32(addrlen, vptr + 2 * n))
  1274. return -TARGET_EFAULT;
  1275. ret = do_bind(sockfd, target_addr, addrlen);
  1276. }
  1277. break;
  1278. case SOCKOP_connect:
  1279. {
  1280. int sockfd;
  1281. abi_ulong target_addr;
  1282. socklen_t addrlen;
  1283. if (get_user_s32(sockfd, vptr)
  1284. || get_user_ual(target_addr, vptr + n)
  1285. || get_user_u32(addrlen, vptr + 2 * n))
  1286. return -TARGET_EFAULT;
  1287. ret = do_connect(sockfd, target_addr, addrlen);
  1288. }
  1289. break;
  1290. case SOCKOP_listen:
  1291. {
  1292. int sockfd, backlog;
  1293. if (get_user_s32(sockfd, vptr)
  1294. || get_user_s32(backlog, vptr + n))
  1295. return -TARGET_EFAULT;
  1296. ret = get_errno(listen(sockfd, backlog));
  1297. }
  1298. break;
  1299. case SOCKOP_accept:
  1300. {
  1301. int sockfd;
  1302. abi_ulong target_addr, target_addrlen;
  1303. if (get_user_s32(sockfd, vptr)
  1304. || get_user_ual(target_addr, vptr + n)
  1305. || get_user_u32(target_addrlen, vptr + 2 * n))
  1306. return -TARGET_EFAULT;
  1307. ret = do_accept(sockfd, target_addr, target_addrlen);
  1308. }
  1309. break;
  1310. case SOCKOP_getsockname:
  1311. {
  1312. int sockfd;
  1313. abi_ulong target_addr, target_addrlen;
  1314. if (get_user_s32(sockfd, vptr)
  1315. || get_user_ual(target_addr, vptr + n)
  1316. || get_user_u32(target_addrlen, vptr + 2 * n))
  1317. return -TARGET_EFAULT;
  1318. ret = do_getsockname(sockfd, target_addr, target_addrlen);
  1319. }
  1320. break;
  1321. case SOCKOP_getpeername:
  1322. {
  1323. int sockfd;
  1324. abi_ulong target_addr, target_addrlen;
  1325. if (get_user_s32(sockfd, vptr)
  1326. || get_user_ual(target_addr, vptr + n)
  1327. || get_user_u32(target_addrlen, vptr + 2 * n))
  1328. return -TARGET_EFAULT;
  1329. ret = do_getpeername(sockfd, target_addr, target_addrlen);
  1330. }
  1331. break;
  1332. case SOCKOP_socketpair:
  1333. {
  1334. int domain, type, protocol;
  1335. abi_ulong tab;
  1336. if (get_user_s32(domain, vptr)
  1337. || get_user_s32(type, vptr + n)
  1338. || get_user_s32(protocol, vptr + 2 * n)
  1339. || get_user_ual(tab, vptr + 3 * n))
  1340. return -TARGET_EFAULT;
  1341. ret = do_socketpair(domain, type, protocol, tab);
  1342. }
  1343. break;
  1344. case SOCKOP_send:
  1345. {
  1346. int sockfd;
  1347. abi_ulong msg;
  1348. size_t len;
  1349. int flags;
  1350. if (get_user_s32(sockfd, vptr)
  1351. || get_user_ual(msg, vptr + n)
  1352. || get_user_ual(len, vptr + 2 * n)
  1353. || get_user_s32(flags, vptr + 3 * n))
  1354. return -TARGET_EFAULT;
  1355. ret = do_sendto(sockfd, msg, len, flags, 0, 0);
  1356. }
  1357. break;
  1358. case SOCKOP_recv:
  1359. {
  1360. int sockfd;
  1361. abi_ulong msg;
  1362. size_t len;
  1363. int flags;
  1364. if (get_user_s32(sockfd, vptr)
  1365. || get_user_ual(msg, vptr + n)
  1366. || get_user_ual(len, vptr + 2 * n)
  1367. || get_user_s32(flags, vptr + 3 * n))
  1368. return -TARGET_EFAULT;
  1369. ret = do_recvfrom(sockfd, msg, len, flags, 0, 0);
  1370. }
  1371. break;
  1372. case SOCKOP_sendto:
  1373. {
  1374. int sockfd;
  1375. abi_ulong msg;
  1376. size_t len;
  1377. int flags;
  1378. abi_ulong addr;
  1379. socklen_t addrlen;
  1380. if (get_user_s32(sockfd, vptr)
  1381. || get_user_ual(msg, vptr + n)
  1382. || get_user_ual(len, vptr + 2 * n)
  1383. || get_user_s32(flags, vptr + 3 * n)
  1384. || get_user_ual(addr, vptr + 4 * n)
  1385. || get_user_u32(addrlen, vptr + 5 * n))
  1386. return -TARGET_EFAULT;
  1387. ret = do_sendto(sockfd, msg, len, flags, addr, addrlen);
  1388. }
  1389. break;
  1390. case SOCKOP_recvfrom:
  1391. {
  1392. int sockfd;
  1393. abi_ulong msg;
  1394. size_t len;
  1395. int flags;
  1396. abi_ulong addr;
  1397. socklen_t addrlen;
  1398. if (get_user_s32(sockfd, vptr)
  1399. || get_user_ual(msg, vptr + n)
  1400. || get_user_ual(len, vptr + 2 * n)
  1401. || get_user_s32(flags, vptr + 3 * n)
  1402. || get_user_ual(addr, vptr + 4 * n)
  1403. || get_user_u32(addrlen, vptr + 5 * n))
  1404. return -TARGET_EFAULT;
  1405. ret = do_recvfrom(sockfd, msg, len, flags, addr, addrlen);
  1406. }
  1407. break;
  1408. case SOCKOP_shutdown:
  1409. {
  1410. int sockfd, how;
  1411. if (get_user_s32(sockfd, vptr)
  1412. || get_user_s32(how, vptr + n))
  1413. return -TARGET_EFAULT;
  1414. ret = get_errno(shutdown(sockfd, how));
  1415. }
  1416. break;
  1417. case SOCKOP_sendmsg:
  1418. case SOCKOP_recvmsg:
  1419. {
  1420. int fd;
  1421. abi_ulong target_msg;
  1422. int flags;
  1423. if (get_user_s32(fd, vptr)
  1424. || get_user_ual(target_msg, vptr + n)
  1425. || get_user_s32(flags, vptr + 2 * n))
  1426. return -TARGET_EFAULT;
  1427. ret = do_sendrecvmsg(fd, target_msg, flags,
  1428. (num == SOCKOP_sendmsg));
  1429. }
  1430. break;
  1431. case SOCKOP_setsockopt:
  1432. {
  1433. int sockfd;
  1434. int level;
  1435. int optname;
  1436. abi_ulong optval;
  1437. socklen_t optlen;
  1438. if (get_user_s32(sockfd, vptr)
  1439. || get_user_s32(level, vptr + n)
  1440. || get_user_s32(optname, vptr + 2 * n)
  1441. || get_user_ual(optval, vptr + 3 * n)
  1442. || get_user_u32(optlen, vptr + 4 * n))
  1443. return -TARGET_EFAULT;
  1444. ret = do_setsockopt(sockfd, level, optname, optval, optlen);
  1445. }
  1446. break;
  1447. case SOCKOP_getsockopt:
  1448. {
  1449. int sockfd;
  1450. int level;
  1451. int optname;
  1452. abi_ulong optval;
  1453. socklen_t optlen;
  1454. if (get_user_s32(sockfd, vptr)
  1455. || get_user_s32(level, vptr + n)
  1456. || get_user_s32(optname, vptr + 2 * n)
  1457. || get_user_ual(optval, vptr + 3 * n)
  1458. || get_user_u32(optlen, vptr + 4 * n))
  1459. return -TARGET_EFAULT;
  1460. ret = do_getsockopt(sockfd, level, optname, optval, optlen);
  1461. }
  1462. break;
  1463. default:
  1464. gemu_log("Unsupported socketcall: %d\n", num);
  1465. ret = -TARGET_ENOSYS;
  1466. break;
  1467. }
  1468. return ret;
  1469. }
  1470. #endif
  1471. #ifdef TARGET_NR_ipc
  1472. #define N_SHM_REGIONS 32
  1473. static struct shm_region {
  1474. abi_ulong start;
  1475. abi_ulong size;
  1476. } shm_regions[N_SHM_REGIONS];
  1477. #endif
  1478. struct target_ipc_perm
  1479. {
  1480. abi_long __key;
  1481. abi_ulong uid;
  1482. abi_ulong gid;
  1483. abi_ulong cuid;
  1484. abi_ulong cgid;
  1485. unsigned short int mode;
  1486. unsigned short int __pad1;
  1487. unsigned short int __seq;
  1488. unsigned short int __pad2;
  1489. abi_ulong __unused1;
  1490. abi_ulong __unused2;
  1491. };
  1492. struct target_semid_ds
  1493. {
  1494. struct target_ipc_perm sem_perm;
  1495. abi_ulong sem_otime;
  1496. abi_ulong __unused1;
  1497. abi_ulong sem_ctime;
  1498. abi_ulong __unused2;
  1499. abi_ulong sem_nsems;
  1500. abi_ulong __unused3;
  1501. abi_ulong __unused4;
  1502. };
  1503. static inline abi_long target_to_host_ipc_perm(struct ipc_perm *host_ip,
  1504. abi_ulong target_addr)
  1505. {
  1506. struct target_ipc_perm *target_ip;
  1507. struct target_semid_ds *target_sd;
  1508. if (!lock_user_struct(VERIFY_READ, target_sd, target_addr, 1))
  1509. return -TARGET_EFAULT;
  1510. target_ip=&(target_sd->sem_perm);
  1511. host_ip->__key = tswapl(target_ip->__key);
  1512. host_ip->uid = tswapl(target_ip->uid);
  1513. host_ip->gid = tswapl(target_ip->gid);
  1514. host_ip->cuid = tswapl(target_ip->cuid);
  1515. host_ip->cgid = tswapl(target_ip->cgid);
  1516. host_ip->mode = tswapl(target_ip->mode);
  1517. unlock_user_struct(target_sd, target_addr, 0);
  1518. return 0;
  1519. }
  1520. static inline abi_long host_to_target_ipc_perm(abi_ulong target_addr,
  1521. struct ipc_perm *host_ip)
  1522. {
  1523. struct target_ipc_perm *target_ip;
  1524. struct target_semid_ds *target_sd;
  1525. if (!lock_user_struct(VERIFY_WRITE, target_sd, target_addr, 0))
  1526. return -TARGET_EFAULT;
  1527. target_ip = &(target_sd->sem_perm);
  1528. target_ip->__key = tswapl(host_ip->__key);
  1529. target_ip->uid = tswapl(host_ip->uid);
  1530. target_ip->gid = tswapl(host_ip->gid);
  1531. target_ip->cuid = tswapl(host_ip->cuid);
  1532. target_ip->cgid = tswapl(host_ip->cgid);
  1533. target_ip->mode = tswapl(host_ip->mode);
  1534. unlock_user_struct(target_sd, target_addr, 1);
  1535. return 0;
  1536. }
  1537. static inline abi_long target_to_host_semid_ds(struct semid_ds *host_sd,
  1538. abi_ulong target_addr)
  1539. {
  1540. struct target_semid_ds *target_sd;
  1541. if (!lock_user_struct(VERIFY_READ, target_sd, target_addr, 1))
  1542. return -TARGET_EFAULT;
  1543. target_to_host_ipc_perm(&(host_sd->sem_perm),target_addr);
  1544. host_sd->sem_nsems = tswapl(target_sd->sem_nsems);
  1545. host_sd->sem_otime = tswapl(target_sd->sem_otime);
  1546. host_sd->sem_ctime = tswapl(target_sd->sem_ctime);
  1547. unlock_user_struct(target_sd, target_addr, 0);
  1548. return 0;
  1549. }
  1550. static inline abi_long host_to_target_semid_ds(abi_ulong target_addr,
  1551. struct semid_ds *host_sd)
  1552. {
  1553. struct target_semid_ds *target_sd;
  1554. if (!lock_user_struct(VERIFY_WRITE, target_sd, target_addr, 0))
  1555. return -TARGET_EFAULT;
  1556. host_to_target_ipc_perm(target_addr,&(host_sd->sem_perm));
  1557. target_sd->sem_nsems = tswapl(host_sd->sem_nsems);
  1558. target_sd->sem_otime = tswapl(host_sd->sem_otime);
  1559. target_sd->sem_ctime = tswapl(host_sd->sem_ctime);
  1560. unlock_user_struct(target_sd, target_addr, 1);
  1561. return 0;
  1562. }
  1563. union semun {
  1564. int val;
  1565. struct semid_ds *buf;
  1566. unsigned short *array;
  1567. };
  1568. union target_semun {
  1569. int val;
  1570. abi_long buf;
  1571. unsigned short int *array;
  1572. };
  1573. static inline abi_long target_to_host_semun(int cmd,
  1574. union semun *host_su,
  1575. abi_ulong target_addr,
  1576. struct semid_ds *ds)
  1577. {
  1578. union target_semun *target_su;
  1579. switch( cmd ) {
  1580. case IPC_STAT:
  1581. case IPC_SET:
  1582. if (!lock_user_struct(VERIFY_READ, target_su, target_addr, 1))
  1583. return -TARGET_EFAULT;
  1584. target_to_host_semid_ds(ds,target_su->buf);
  1585. host_su->buf = ds;
  1586. unlock_user_struct(target_su, target_addr, 0);
  1587. break;
  1588. case GETVAL:
  1589. case SETVAL:
  1590. if (!lock_user_struct(VERIFY_READ, target_su, target_addr, 1))
  1591. return -TARGET_EFAULT;
  1592. host_su->val = tswapl(target_su->val);
  1593. unlock_user_struct(target_su, target_addr, 0);
  1594. break;
  1595. case GETALL:
  1596. case SETALL:
  1597. if (!lock_user_struct(VERIFY_READ, target_su, target_addr, 1))
  1598. return -TARGET_EFAULT;
  1599. *host_su->array = tswap16(*target_su->array);
  1600. unlock_user_struct(target_su, target_addr, 0);
  1601. break;
  1602. default:
  1603. gemu_log("semun operation not fully supported: %d\n", (int)cmd);
  1604. }
  1605. return 0;
  1606. }
  1607. static inline abi_long host_to_target_semun(int cmd,
  1608. abi_ulong target_addr,
  1609. union semun *host_su,
  1610. struct semid_ds *ds)
  1611. {
  1612. union target_semun *target_su;
  1613. switch( cmd ) {
  1614. case IPC_STAT:
  1615. case IPC_SET:
  1616. if (lock_user_struct(VERIFY_WRITE, target_su, target_addr, 0))
  1617. return -TARGET_EFAULT;
  1618. host_to_target_semid_ds(target_su->buf,ds);
  1619. unlock_user_struct(target_su, target_addr, 1);
  1620. break;
  1621. case GETVAL:
  1622. case SETVAL:
  1623. if (lock_user_struct(VERIFY_WRITE, target_su, target_addr, 0))
  1624. return -TARGET_EFAULT;
  1625. target_su->val = tswapl(host_su->val);
  1626. unlock_user_struct(target_su, target_addr, 1);
  1627. break;
  1628. case GETALL:
  1629. case SETALL:
  1630. if (lock_user_struct(VERIFY_WRITE, target_su, target_addr, 0))
  1631. return -TARGET_EFAULT;
  1632. *target_su->array = tswap16(*host_su->array);
  1633. unlock_user_struct(target_su, target_addr, 1);
  1634. break;
  1635. default:
  1636. gemu_log("semun operation not fully supported: %d\n", (int)cmd);
  1637. }
  1638. return 0;
  1639. }
  1640. static inline abi_long do_semctl(int first, int second, int third,
  1641. abi_long ptr)
  1642. {
  1643. union semun arg;
  1644. struct semid_ds dsarg;
  1645. int cmd = third&0xff;
  1646. abi_long ret = 0;
  1647. switch( cmd ) {
  1648. case GETVAL:
  1649. target_to_host_semun(cmd,&arg,ptr,&dsarg);
  1650. ret = get_errno(semctl(first, second, cmd, arg));
  1651. host_to_target_semun(cmd,ptr,&arg,&dsarg);
  1652. break;
  1653. case SETVAL:
  1654. target_to_host_semun(cmd,&arg,ptr,&dsarg);
  1655. ret = get_errno(semctl(first, second, cmd, arg));
  1656. host_to_target_semun(cmd,ptr,&arg,&dsarg);
  1657. break;
  1658. case GETALL:
  1659. target_to_host_semun(cmd,&arg,ptr,&dsarg);
  1660. ret = get_errno(semctl(first, second, cmd, arg));
  1661. host_to_target_semun(cmd,ptr,&arg,&dsarg);
  1662. break;
  1663. case SETALL:
  1664. target_to_host_semun(cmd,&arg,ptr,&dsarg);
  1665. ret = get_errno(semctl(first, second, cmd, arg));
  1666. host_to_target_semun(cmd,ptr,&arg,&dsarg);
  1667. break;
  1668. case IPC_STAT:
  1669. target_to_host_semun(cmd,&arg,ptr,&dsarg);
  1670. ret = get_errno(semctl(first, second, cmd, arg));
  1671. host_to_target_semun(cmd,ptr,&arg,&dsarg);
  1672. break;
  1673. case IPC_SET:
  1674. target_to_host_semun(cmd,&arg,ptr,&dsarg);
  1675. ret = get_errno(semctl(first, second, cmd, arg));
  1676. host_to_target_semun(cmd,ptr,&arg,&dsarg);
  1677. break;
  1678. default:
  1679. ret = get_errno(semctl(first, second, cmd, arg));
  1680. }
  1681. return ret;
  1682. }
  1683. struct target_msqid_ds
  1684. {
  1685. struct target_ipc_perm msg_perm;
  1686. abi_ulong msg_stime;
  1687. #if TARGET_ABI_BITS == 32
  1688. abi_ulong __unused1;
  1689. #endif
  1690. abi_ulong msg_rtime;
  1691. #if TARGET_ABI_BITS == 32
  1692. abi_ulong __unused2;
  1693. #endif
  1694. abi_ulong msg_ctime;
  1695. #if TARGET_ABI_BITS == 32
  1696. abi_ulong __unused3;
  1697. #endif
  1698. abi_ulong __msg_cbytes;
  1699. abi_ulong msg_qnum;
  1700. abi_ulong msg_qbytes;
  1701. abi_ulong msg_lspid;
  1702. abi_ulong msg_lrpid;
  1703. abi_ulong __unused4;
  1704. abi_ulong __unused5;
  1705. };
  1706. static inline abi_long target_to_host_msqid_ds(struct msqid_ds *host_md,
  1707. abi_ulong target_addr)
  1708. {
  1709. struct target_msqid_ds *target_md;
  1710. if (!lock_user_struct(VERIFY_READ, target_md, target_addr, 1))
  1711. return -TARGET_EFAULT;
  1712. if (target_to_host_ipc_perm(&(host_md->msg_perm),target_addr))
  1713. return -TARGET_EFAULT;
  1714. host_md->msg_stime = tswapl(target_md->msg_stime);
  1715. host_md->msg_rtime = tswapl(target_md->msg_rtime);
  1716. host_md->msg_ctime = tswapl(target_md->msg_ctime);
  1717. host_md->__msg_cbytes = tswapl(target_md->__msg_cbytes);
  1718. host_md->msg_qnum = tswapl(target_md->msg_qnum);
  1719. host_md->msg_qbytes = tswapl(target_md->msg_qbytes);
  1720. host_md->msg_lspid = tswapl(target_md->msg_lspid);
  1721. host_md->msg_lrpid = tswapl(target_md->msg_lrpid);
  1722. unlock_user_struct(target_md, target_addr, 0);
  1723. return 0;
  1724. }
  1725. static inline abi_long host_to_target_msqid_ds(abi_ulong target_addr,
  1726. struct msqid_ds *host_md)
  1727. {
  1728. struct target_msqid_ds *target_md;
  1729. if (!lock_user_struct(VERIFY_WRITE, target_md, target_addr, 0))
  1730. return -TARGET_EFAULT;
  1731. if (host_to_target_ipc_perm(target_addr,&(host_md->msg_perm)))
  1732. return -TARGET_EFAULT;
  1733. target_md->msg_stime = tswapl(host_md->msg_stime);
  1734. target_md->msg_rtime = tswapl(host_md->msg_rtime);
  1735. target_md->msg_ctime = tswapl(host_md->msg_ctime);
  1736. target_md->__msg_cbytes = tswapl(host_md->__msg_cbytes);
  1737. target_md->msg_qnum = tswapl(host_md->msg_qnum);
  1738. target_md->msg_qbytes = tswapl(host_md->msg_qbytes);
  1739. target_md->msg_lspid = tswapl(host_md->msg_lspid);
  1740. target_md->msg_lrpid = tswapl(host_md->msg_lrpid);
  1741. unlock_user_struct(target_md, target_addr, 1);
  1742. return 0;
  1743. }
  1744. struct target_msginfo {
  1745. int msgpool;
  1746. int msgmap;
  1747. int msgmax;
  1748. int msgmnb;
  1749. int msgmni;
  1750. int msgssz;
  1751. int msgtql;
  1752. unsigned short int msgseg;
  1753. };
  1754. static inline abi_long host_to_target_msginfo(abi_ulong target_addr,
  1755. struct msginfo *host_msginfo)
  1756. {
  1757. struct target_msginfo *target_msginfo;
  1758. if (!lock_user_struct(VERIFY_WRITE, target_msginfo, target_addr, 0))
  1759. return -TARGET_EFAULT;
  1760. __put_user(host_msginfo->msgpool, &target_msginfo->msgpool);
  1761. __put_user(host_msginfo->msgmap, &target_msginfo->msgmap);
  1762. __put_user(host_msginfo->msgmax, &target_msginfo->msgmax);
  1763. __put_user(host_msginfo->msgmnb, &target_msginfo->msgmnb);
  1764. __put_user(host_msginfo->msgmni, &target_msginfo->msgmni);
  1765. __put_user(host_msginfo->msgssz, &target_msginfo->msgssz);
  1766. __put_user(host_msginfo->msgtql, &target_msginfo->msgtql);
  1767. __put_user(host_msginfo->msgseg, &target_msginfo->msgseg);
  1768. unlock_user_struct(target_msginfo, target_addr, 1);
  1769. return 0;
  1770. }
  1771. static inline abi_long do_msgctl(int msgid, int cmd, abi_long ptr)
  1772. {
  1773. struct msqid_ds dsarg;
  1774. struct msginfo msginfo;
  1775. abi_long ret = -TARGET_EINVAL;
  1776. cmd &= 0xff;
  1777. switch (cmd) {
  1778. case IPC_STAT:
  1779. case IPC_SET:
  1780. case MSG_STAT:
  1781. if (target_to_host_msqid_ds(&dsarg,ptr))
  1782. return -TARGET_EFAULT;
  1783. ret = get_errno(msgctl(msgid, cmd, &dsarg));
  1784. if (host_to_target_msqid_ds(ptr,&dsarg))
  1785. return -TARGET_EFAULT;
  1786. break;
  1787. case IPC_RMID:
  1788. ret = get_errno(msgctl(msgid, cmd, NULL));
  1789. break;
  1790. case IPC_INFO:
  1791. case MSG_INFO:
  1792. ret = get_errno(msgctl(msgid, cmd, (struct msqid_ds *)&msginfo));
  1793. if (host_to_target_msginfo(ptr, &msginfo))
  1794. return -TARGET_EFAULT;
  1795. break;
  1796. }
  1797. return ret;
  1798. }
  1799. struct target_msgbuf {
  1800. abi_long mtype;
  1801. char mtext[1];
  1802. };
  1803. static inline abi_long do_msgsnd(int msqid, abi_long msgp,
  1804. unsigned int msgsz, int msgflg)
  1805. {
  1806. struct target_msgbuf *target_mb;
  1807. struct msgbuf *host_mb;
  1808. abi_long ret = 0;
  1809. if (!lock_user_struct(VERIFY_READ, target_mb, msgp, 0))
  1810. return -TARGET_EFAULT;
  1811. host_mb = malloc(msgsz+sizeof(long));
  1812. host_mb->mtype = (abi_long) tswapl(target_mb->mtype);
  1813. memcpy(host_mb->mtext, target_mb->mtext, msgsz);
  1814. ret = get_errno(msgsnd(msqid, host_mb, msgsz, msgflg));
  1815. free(host_mb);
  1816. unlock_user_struct(target_mb, msgp, 0);
  1817. return ret;
  1818. }
  1819. static inline abi_long do_msgrcv(int msqid, abi_long msgp,
  1820. unsigned int msgsz, abi_long msgtyp,
  1821. int msgflg)
  1822. {
  1823. struct target_msgbuf *target_mb;
  1824. char *target_mtext;
  1825. struct msgbuf *host_mb;
  1826. abi_long ret = 0;
  1827. if (!lock_user_struct(VERIFY_WRITE, target_mb, msgp, 0))
  1828. return -TARGET_EFAULT;
  1829. host_mb = malloc(msgsz+sizeof(long));
  1830. ret = get_errno(msgrcv(msqid, host_mb, msgsz, tswapl(msgtyp), msgflg));
  1831. if (ret > 0) {
  1832. abi_ulong target_mtext_addr = msgp + sizeof(abi_ulong);
  1833. target_mtext = lock_user(VERIFY_WRITE, target_mtext_addr, ret, 0);
  1834. if (!target_mtext) {
  1835. ret = -TARGET_EFAULT;
  1836. goto end;
  1837. }
  1838. memcpy(target_mb->mtext, host_mb->mtext, ret);
  1839. unlock_user(target_mtext, target_mtext_addr, ret);
  1840. }
  1841. target_mb->mtype = tswapl(host_mb->mtype);
  1842. free(host_mb);
  1843. end:
  1844. if (target_mb)
  1845. unlock_user_struct(target_mb, msgp, 1);
  1846. return ret;
  1847. }
  1848. #ifdef TARGET_NR_ipc
  1849. /* ??? This only works with linear mappings. */
  1850. /* do_ipc() must return target values and target errnos. */
  1851. static abi_long do_ipc(unsigned int call, int first,
  1852. int second, int third,
  1853. abi_long ptr, abi_long fifth)
  1854. {
  1855. int version;
  1856. abi_long ret = 0;
  1857. struct shmid_ds shm_info;
  1858. int i;
  1859. version = call >> 16;
  1860. call &= 0xffff;
  1861. switch (call) {
  1862. case IPCOP_semop:
  1863. ret = get_errno(semop(first,(struct sembuf *)g2h(ptr), second));
  1864. break;
  1865. case IPCOP_semget:
  1866. ret = get_errno(semget(first, second, third));
  1867. break;
  1868. case IPCOP_semctl:
  1869. ret = do_semctl(first, second, third, ptr);
  1870. break;
  1871. case IPCOP_semtimedop:
  1872. gemu_log("Unsupported ipc call: %d (version %d)\n", call, version);
  1873. ret = -TARGET_ENOSYS;
  1874. break;
  1875. case IPCOP_msgget:
  1876. ret = get_errno(msgget(first, second));
  1877. break;
  1878. case IPCOP_msgsnd:
  1879. ret = do_msgsnd(first, ptr, second, third);
  1880. break;
  1881. case IPCOP_msgctl:
  1882. ret = do_msgctl(first, second, ptr);
  1883. break;
  1884. case IPCOP_msgrcv:
  1885. switch (version) {
  1886. case 0:
  1887. {
  1888. struct target_ipc_kludge {
  1889. abi_long msgp;
  1890. abi_long msgtyp;
  1891. } *tmp;
  1892. if (!lock_user_struct(VERIFY_READ, tmp, ptr, 1)) {
  1893. ret = -TARGET_EFAULT;
  1894. break;
  1895. }
  1896. ret = do_msgrcv(first, tmp->msgp, second, tmp->msgtyp, third);
  1897. unlock_user_struct(tmp, ptr, 0);
  1898. break;
  1899. }
  1900. default:
  1901. ret = do_msgrcv(first, ptr, second, fifth, third);
  1902. }
  1903. break;
  1904. case IPCOP_shmat:
  1905. {
  1906. abi_ulong raddr;
  1907. void *host_addr;
  1908. /* SHM_* flags are the same on all linux platforms */
  1909. host_addr = shmat(first, (void *)g2h(ptr), second);
  1910. if (host_addr == (void *)-1) {
  1911. ret = get_errno((long)host_addr);
  1912. break;
  1913. }
  1914. raddr = h2g((unsigned long)host_addr);
  1915. /* find out the length of the shared memory segment */
  1916. ret = get_errno(shmctl(first, IPC_STAT, &shm_info));
  1917. if (is_error(ret)) {
  1918. /* can't get length, bail out */
  1919. shmdt(host_addr);
  1920. break;
  1921. }
  1922. page_set_flags(raddr, raddr + shm_info.shm_segsz,
  1923. PAGE_VALID | PAGE_READ |
  1924. ((second & SHM_RDONLY)? 0: PAGE_WRITE));
  1925. for (i = 0; i < N_SHM_REGIONS; ++i) {
  1926. if (shm_regions[i].start == 0) {
  1927. shm_regions[i].start = raddr;
  1928. shm_regions[i].size = shm_info.shm_segsz;
  1929. break;
  1930. }
  1931. }
  1932. if (put_user_ual(raddr, third))
  1933. return -TARGET_EFAULT;
  1934. ret = 0;
  1935. }
  1936. break;
  1937. case IPCOP_shmdt:
  1938. for (i = 0; i < N_SHM_REGIONS; ++i) {
  1939. if (shm_regions[i].start == ptr) {
  1940. shm_regions[i].start = 0;
  1941. page_set_flags(ptr, shm_regions[i].size, 0);
  1942. break;
  1943. }
  1944. }
  1945. ret = get_errno(shmdt((void *)g2h(ptr)));
  1946. break;
  1947. case IPCOP_shmget:
  1948. /* IPC_* flag values are the same on all linux platforms */
  1949. ret = get_errno(shmget(first, second, third));
  1950. break;
  1951. /* IPC_* and SHM_* command values are the same on all linux platforms */
  1952. case IPCOP_shmctl:
  1953. switch(second) {
  1954. case IPC_RMID:
  1955. case SHM_LOCK:
  1956. case SHM_UNLOCK:
  1957. ret = get_errno(shmctl(first, second, NULL));
  1958. break;
  1959. default:
  1960. goto unimplemented;
  1961. }
  1962. break;
  1963. default:
  1964. unimplemented:
  1965. gemu_log("Unsupported ipc call: %d (version %d)\n", call, version);
  1966. ret = -TARGET_ENOSYS;
  1967. break;
  1968. }
  1969. return ret;
  1970. }
  1971. #endif
  1972. /* kernel structure types definitions */
  1973. #define IFNAMSIZ 16
  1974. #define STRUCT(name, list...) STRUCT_ ## name,
  1975. #define STRUCT_SPECIAL(name) STRUCT_ ## name,
  1976. enum {
  1977. #include "syscall_types.h"
  1978. };
  1979. #undef STRUCT
  1980. #undef STRUCT_SPECIAL
  1981. #define STRUCT(name, list...) static const argtype struct_ ## name ## _def[] = { list, TYPE_NULL };
  1982. #define STRUCT_SPECIAL(name)
  1983. #include "syscall_types.h"
  1984. #undef STRUCT
  1985. #undef STRUCT_SPECIAL
  1986. typedef struct IOCTLEntry {
  1987. unsigned int target_cmd;
  1988. unsigned int host_cmd;
  1989. const char *name;
  1990. int access;
  1991. const argtype arg_type[5];
  1992. } IOCTLEntry;
  1993. #define IOC_R 0x0001
  1994. #define IOC_W 0x0002
  1995. #define IOC_RW (IOC_R | IOC_W)
  1996. #define MAX_STRUCT_SIZE 4096
  1997. static IOCTLEntry ioctl_entries[] = {
  1998. #define IOCTL(cmd, access, types...) \
  1999. { TARGET_ ## cmd, cmd, #cmd, access, { types } },
  2000. #include "ioctls.h"
  2001. { 0, 0, },
  2002. };
  2003. /* ??? Implement proper locking for ioctls. */
  2004. /* do_ioctl() Must return target values and target errnos. */
  2005. static abi_long do_ioctl(int fd, abi_long cmd, abi_long arg)
  2006. {
  2007. const IOCTLEntry *ie;
  2008. const argtype *arg_type;
  2009. abi_long ret;
  2010. uint8_t buf_temp[MAX_STRUCT_SIZE];
  2011. int target_size;
  2012. void *argptr;
  2013. ie = ioctl_entries;
  2014. for(;;) {
  2015. if (ie->target_cmd == 0) {
  2016. gemu_log("Unsupported ioctl: cmd=0x%04lx\n", (long)cmd);
  2017. return -TARGET_ENOSYS;
  2018. }
  2019. if (ie->target_cmd == cmd)
  2020. break;
  2021. ie++;
  2022. }
  2023. arg_type = ie->arg_type;
  2024. #if defined(DEBUG)
  2025. gemu_log("ioctl: cmd=0x%04lx (%s)\n", (long)cmd, ie->name);
  2026. #endif
  2027. switch(arg_type[0]) {
  2028. case TYPE_NULL:
  2029. /* no argument */
  2030. ret = get_errno(ioctl(fd, ie->host_cmd));
  2031. break;
  2032. case TYPE_PTRVOID:
  2033. case TYPE_INT:
  2034. /* int argment */
  2035. ret = get_errno(ioctl(fd, ie->host_cmd, arg));
  2036. break;
  2037. case TYPE_PTR:
  2038. arg_type++;
  2039. target_size = thunk_type_size(arg_type, 0);
  2040. switch(ie->access) {
  2041. case IOC_R:
  2042. ret = get_errno(ioctl(fd, ie->host_cmd, buf_temp));
  2043. if (!is_error(ret)) {
  2044. argptr = lock_user(VERIFY_WRITE, arg, target_size, 0);
  2045. if (!argptr)
  2046. return -TARGET_EFAULT;
  2047. thunk_convert(argptr, buf_temp, arg_type, THUNK_TARGET);
  2048. unlock_user(argptr, arg, target_size);
  2049. }
  2050. break;
  2051. case IOC_W:
  2052. argptr = lock_user(VERIFY_READ, arg, target_size, 1);
  2053. if (!argptr)
  2054. return -TARGET_EFAULT;
  2055. thunk_convert(buf_temp, argptr, arg_type, THUNK_HOST);
  2056. unlock_user(argptr, arg, 0);
  2057. ret = get_errno(ioctl(fd, ie->host_cmd, buf_temp));
  2058. break;
  2059. default:
  2060. case IOC_RW:
  2061. argptr = lock_user(VERIFY_READ, arg, target_size, 1);
  2062. if (!argptr)
  2063. return -TARGET_EFAULT;
  2064. thunk_convert(buf_temp, argptr, arg_type, THUNK_HOST);
  2065. unlock_user(argptr, arg, 0);
  2066. ret = get_errno(ioctl(fd, ie->host_cmd, buf_temp));
  2067. if (!is_error(ret)) {
  2068. argptr = lock_user(VERIFY_WRITE, arg, target_size, 0);
  2069. if (!argptr)
  2070. return -TARGET_EFAULT;
  2071. thunk_convert(argptr, buf_temp, arg_type, THUNK_TARGET);
  2072. unlock_user(argptr, arg, target_size);
  2073. }
  2074. break;
  2075. }
  2076. break;
  2077. default:
  2078. gemu_log("Unsupported ioctl type: cmd=0x%04lx type=%d\n",
  2079. (long)cmd, arg_type[0]);
  2080. ret = -TARGET_ENOSYS;
  2081. break;
  2082. }
  2083. return ret;
  2084. }
  2085. static const bitmask_transtbl iflag_tbl[] = {
  2086. { TARGET_IGNBRK, TARGET_IGNBRK, IGNBRK, IGNBRK },
  2087. { TARGET_BRKINT, TARGET_BRKINT, BRKINT, BRKINT },
  2088. { TARGET_IGNPAR, TARGET_IGNPAR, IGNPAR, IGNPAR },
  2089. { TARGET_PARMRK, TARGET_PARMRK, PARMRK, PARMRK },
  2090. { TARGET_INPCK, TARGET_INPCK, INPCK, INPCK },
  2091. { TARGET_ISTRIP, TARGET_ISTRIP, ISTRIP, ISTRIP },
  2092. { TARGET_INLCR, TARGET_INLCR, INLCR, INLCR },
  2093. { TARGET_IGNCR, TARGET_IGNCR, IGNCR, IGNCR },
  2094. { TARGET_ICRNL, TARGET_ICRNL, ICRNL, ICRNL },
  2095. { TARGET_IUCLC, TARGET_IUCLC, IUCLC, IUCLC },
  2096. { TARGET_IXON, TARGET_IXON, IXON, IXON },
  2097. { TARGET_IXANY, TARGET_IXANY, IXANY, IXANY },
  2098. { TARGET_IXOFF, TARGET_IXOFF, IXOFF, IXOFF },
  2099. { TARGET_IMAXBEL, TARGET_IMAXBEL, IMAXBEL, IMAXBEL },
  2100. { 0, 0, 0, 0 }
  2101. };
  2102. static const bitmask_transtbl oflag_tbl[] = {
  2103. { TARGET_OPOST, TARGET_OPOST, OPOST, OPOST },
  2104. { TARGET_OLCUC, TARGET_OLCUC, OLCUC, OLCUC },
  2105. { TARGET_ONLCR, TARGET_ONLCR, ONLCR, ONLCR },
  2106. { TARGET_OCRNL, TARGET_OCRNL, OCRNL, OCRNL },
  2107. { TARGET_ONOCR, TARGET_ONOCR, ONOCR, ONOCR },
  2108. { TARGET_ONLRET, TARGET_ONLRET, ONLRET, ONLRET },
  2109. { TARGET_OFILL, TARGET_OFILL, OFILL, OFILL },
  2110. { TARGET_OFDEL, TARGET_OFDEL, OFDEL, OFDEL },
  2111. { TARGET_NLDLY, TARGET_NL0, NLDLY, NL0 },
  2112. { TARGET_NLDLY, TARGET_NL1, NLDLY, NL1 },
  2113. { TARGET_CRDLY, TARGET_CR0, CRDLY, CR0 },
  2114. { TARGET_CRDLY, TARGET_CR1, CRDLY, CR1 },
  2115. { TARGET_CRDLY, TARGET_CR2, CRDLY, CR2 },
  2116. { TARGET_CRDLY, TARGET_CR3, CRDLY, CR3 },
  2117. { TARGET_TABDLY, TARGET_TAB0, TABDLY, TAB0 },
  2118. { TARGET_TABDLY, TARGET_TAB1, TABDLY, TAB1 },
  2119. { TARGET_TABDLY, TARGET_TAB2, TABDLY, TAB2 },
  2120. { TARGET_TABDLY, TARGET_TAB3, TABDLY, TAB3 },
  2121. { TARGET_BSDLY, TARGET_BS0, BSDLY, BS0 },
  2122. { TARGET_BSDLY, TARGET_BS1, BSDLY, BS1 },
  2123. { TARGET_VTDLY, TARGET_VT0, VTDLY, VT0 },
  2124. { TARGET_VTDLY, TARGET_VT1, VTDLY, VT1 },
  2125. { TARGET_FFDLY, TARGET_FF0, FFDLY, FF0 },
  2126. { TARGET_FFDLY, TARGET_FF1, FFDLY, FF1 },
  2127. { 0, 0, 0, 0 }
  2128. };
  2129. static const bitmask_transtbl cflag_tbl[] = {
  2130. { TARGET_CBAUD, TARGET_B0, CBAUD, B0 },
  2131. { TARGET_CBAUD, TARGET_B50, CBAUD, B50 },
  2132. { TARGET_CBAUD, TARGET_B75, CBAUD, B75 },
  2133. { TARGET_CBAUD, TARGET_B110, CBAUD, B110 },
  2134. { TARGET_CBAUD, TARGET_B134, CBAUD, B134 },
  2135. { TARGET_CBAUD, TARGET_B150, CBAUD, B150 },
  2136. { TARGET_CBAUD, TARGET_B200, CBAUD, B200 },
  2137. { TARGET_CBAUD, TARGET_B300, CBAUD, B300 },
  2138. { TARGET_CBAUD, TARGET_B600, CBAUD, B600 },
  2139. { TARGET_CBAUD, TARGET_B1200, CBAUD, B1200 },
  2140. { TARGET_CBAUD, TARGET_B1800, CBAUD, B1800 },
  2141. { TARGET_CBAUD, TARGET_B2400, CBAUD, B2400 },
  2142. { TARGET_CBAUD, TARGET_B4800, CBAUD, B4800 },
  2143. { TARGET_CBAUD, TARGET_B9600, CBAUD, B9600 },
  2144. { TARGET_CBAUD, TARGET_B19200, CBAUD, B19200 },
  2145. { TARGET_CBAUD, TARGET_B38400, CBAUD, B38400 },
  2146. { TARGET_CBAUD, TARGET_B57600, CBAUD, B57600 },
  2147. { TARGET_CBAUD, TARGET_B115200, CBAUD, B115200 },
  2148. { TARGET_CBAUD, TARGET_B230400, CBAUD, B230400 },
  2149. { TARGET_CBAUD, TARGET_B460800, CBAUD, B460800 },
  2150. { TARGET_CSIZE, TARGET_CS5, CSIZE, CS5 },
  2151. { TARGET_CSIZE, TARGET_CS6, CSIZE, CS6 },
  2152. { TARGET_CSIZE, TARGET_CS7, CSIZE, CS7 },
  2153. { TARGET_CSIZE, TARGET_CS8, CSIZE, CS8 },
  2154. { TARGET_CSTOPB, TARGET_CSTOPB, CSTOPB, CSTOPB },
  2155. { TARGET_CREAD, TARGET_CREAD, CREAD, CREAD },
  2156. { TARGET_PARENB, TARGET_PARENB, PARENB, PARENB },
  2157. { TARGET_PARODD, TARGET_PARODD, PARODD, PARODD },
  2158. { TARGET_HUPCL, TARGET_HUPCL, HUPCL, HUPCL },
  2159. { TARGET_CLOCAL, TARGET_CLOCAL, CLOCAL, CLOCAL },
  2160. { TARGET_CRTSCTS, TARGET_CRTSCTS, CRTSCTS, CRTSCTS },
  2161. { 0, 0, 0, 0 }
  2162. };
  2163. static const bitmask_transtbl lflag_tbl[] = {
  2164. { TARGET_ISIG, TARGET_ISIG, ISIG, ISIG },
  2165. { TARGET_ICANON, TARGET_ICANON, ICANON, ICANON },
  2166. { TARGET_XCASE, TARGET_XCASE, XCASE, XCASE },
  2167. { TARGET_ECHO, TARGET_ECHO, ECHO, ECHO },
  2168. { TARGET_ECHOE, TARGET_ECHOE, ECHOE, ECHOE },
  2169. { TARGET_ECHOK, TARGET_ECHOK, ECHOK, ECHOK },
  2170. { TARGET_ECHONL, TARGET_ECHONL, ECHONL, ECHONL },
  2171. { TARGET_NOFLSH, TARGET_NOFLSH, NOFLSH, NOFLSH },
  2172. { TARGET_TOSTOP, TARGET_TOSTOP, TOSTOP, TOSTOP },
  2173. { TARGET_ECHOCTL, TARGET_ECHOCTL, ECHOCTL, ECHOCTL },
  2174. { TARGET_ECHOPRT, TARGET_ECHOPRT, ECHOPRT, ECHOPRT },
  2175. { TARGET_ECHOKE, TARGET_ECHOKE, ECHOKE, ECHOKE },
  2176. { TARGET_FLUSHO, TARGET_FLUSHO, FLUSHO, FLUSHO },
  2177. { TARGET_PENDIN, TARGET_PENDIN, PENDIN, PENDIN },
  2178. { TARGET_IEXTEN, TARGET_IEXTEN, IEXTEN, IEXTEN },
  2179. { 0, 0, 0, 0 }
  2180. };
  2181. static void target_to_host_termios (void *dst, const void *src)
  2182. {
  2183. struct host_termios *host = dst;
  2184. const struct target_termios *target = src;
  2185. host->c_iflag =
  2186. target_to_host_bitmask(tswap32(target->c_iflag), iflag_tbl);
  2187. host->c_oflag =
  2188. target_to_host_bitmask(tswap32(target->c_oflag), oflag_tbl);
  2189. host->c_cflag =
  2190. target_to_host_bitmask(tswap32(target->c_cflag), cflag_tbl);
  2191. host->c_lflag =
  2192. target_to_host_bitmask(tswap32(target->c_lflag), lflag_tbl);
  2193. host->c_line = target->c_line;
  2194. host->c_cc[VINTR] = target->c_cc[TARGET_VINTR];
  2195. host->c_cc[VQUIT] = target->c_cc[TARGET_VQUIT];
  2196. host->c_cc[VERASE] = target->c_cc[TARGET_VERASE];
  2197. host->c_cc[VKILL] = target->c_cc[TARGET_VKILL];
  2198. host->c_cc[VEOF] = target->c_cc[TARGET_VEOF];
  2199. host->c_cc[VTIME] = target->c_cc[TARGET_VTIME];
  2200. host->c_cc[VMIN] = target->c_cc[TARGET_VMIN];
  2201. host->c_cc[VSWTC] = target->c_cc[TARGET_VSWTC];
  2202. host->c_cc[VSTART] = target->c_cc[TARGET_VSTART];
  2203. host->c_cc[VSTOP] = target->c_cc[TARGET_VSTOP];
  2204. host->c_cc[VSUSP] = target->c_cc[TARGET_VSUSP];
  2205. host->c_cc[VEOL] = target->c_cc[TARGET_VEOL];
  2206. host->c_cc[VREPRINT] = target->c_cc[TARGET_VREPRINT];
  2207. host->c_cc[VDISCARD] = target->c_cc[TARGET_VDISCARD];
  2208. host->c_cc[VWERASE] = target->c_cc[TARGET_VWERASE];
  2209. host->c_cc[VLNEXT] = target->c_cc[TARGET_VLNEXT];
  2210. host->c_cc[VEOL2] = target->c_cc[TARGET_VEOL2];
  2211. }
  2212. static void host_to_target_termios (void *dst, const void *src)
  2213. {
  2214. struct target_termios *target = dst;
  2215. const struct host_termios *host = src;
  2216. target->c_iflag =
  2217. tswap32(host_to_target_bitmask(host->c_iflag, iflag_tbl));
  2218. target->c_oflag =
  2219. tswap32(host_to_target_bitmask(host->c_oflag, oflag_tbl));
  2220. target->c_cflag =
  2221. tswap32(host_to_target_bitmask(host->c_cflag, cflag_tbl));
  2222. target->c_lflag =
  2223. tswap32(host_to_target_bitmask(host->c_lflag, lflag_tbl));
  2224. target->c_line = host->c_line;
  2225. target->c_cc[TARGET_VINTR] = host->c_cc[VINTR];
  2226. target->c_cc[TARGET_VQUIT] = host->c_cc[VQUIT];
  2227. target->c_cc[TARGET_VERASE] = host->c_cc[VERASE];
  2228. target->c_cc[TARGET_VKILL] = host->c_cc[VKILL];
  2229. target->c_cc[TARGET_VEOF] = host->c_cc[VEOF];
  2230. target->c_cc[TARGET_VTIME] = host->c_cc[VTIME];
  2231. target->c_cc[TARGET_VMIN] = host->c_cc[VMIN];
  2232. target->c_cc[TARGET_VSWTC] = host->c_cc[VSWTC];
  2233. target->c_cc[TARGET_VSTART] = host->c_cc[VSTART];
  2234. target->c_cc[TARGET_VSTOP] = host->c_cc[VSTOP];
  2235. target->c_cc[TARGET_VSUSP] = host->c_cc[VSUSP];
  2236. target->c_cc[TARGET_VEOL] = host->c_cc[VEOL];
  2237. target->c_cc[TARGET_VREPRINT] = host->c_cc[VREPRINT];
  2238. target->c_cc[TARGET_VDISCARD] = host->c_cc[VDISCARD];
  2239. target->c_cc[TARGET_VWERASE] = host->c_cc[VWERASE];
  2240. target->c_cc[TARGET_VLNEXT] = host->c_cc[VLNEXT];
  2241. target->c_cc[TARGET_VEOL2] = host->c_cc[VEOL2];
  2242. }
  2243. static const StructEntry struct_termios_def = {
  2244. .convert = { host_to_target_termios, target_to_host_termios },
  2245. .size = { sizeof(struct target_termios), sizeof(struct host_termios) },
  2246. .align = { __alignof__(struct target_termios), __alignof__(struct host_termios) },
  2247. };
  2248. static bitmask_transtbl mmap_flags_tbl[] = {
  2249. { TARGET_MAP_SHARED, TARGET_MAP_SHARED, MAP_SHARED, MAP_SHARED },
  2250. { TARGET_MAP_PRIVATE, TARGET_MAP_PRIVATE, MAP_PRIVATE, MAP_PRIVATE },
  2251. { TARGET_MAP_FIXED, TARGET_MAP_FIXED, MAP_FIXED, MAP_FIXED },
  2252. { TARGET_MAP_ANONYMOUS, TARGET_MAP_ANONYMOUS, MAP_ANONYMOUS, MAP_ANONYMOUS },
  2253. { TARGET_MAP_GROWSDOWN, TARGET_MAP_GROWSDOWN, MAP_GROWSDOWN, MAP_GROWSDOWN },
  2254. { TARGET_MAP_DENYWRITE, TARGET_MAP_DENYWRITE, MAP_DENYWRITE, MAP_DENYWRITE },
  2255. { TARGET_MAP_EXECUTABLE, TARGET_MAP_EXECUTABLE, MAP_EXECUTABLE, MAP_EXECUTABLE },
  2256. { TARGET_MAP_LOCKED, TARGET_MAP_LOCKED, MAP_LOCKED, MAP_LOCKED },
  2257. { 0, 0, 0, 0 }
  2258. };
  2259. static bitmask_transtbl fcntl_flags_tbl[] = {
  2260. { TARGET_O_ACCMODE, TARGET_O_WRONLY, O_ACCMODE, O_WRONLY, },
  2261. { TARGET_O_ACCMODE, TARGET_O_RDWR, O_ACCMODE, O_RDWR, },
  2262. { TARGET_O_CREAT, TARGET_O_CREAT, O_CREAT, O_CREAT, },
  2263. { TARGET_O_EXCL, TARGET_O_EXCL, O_EXCL, O_EXCL, },
  2264. { TARGET_O_NOCTTY, TARGET_O_NOCTTY, O_NOCTTY, O_NOCTTY, },
  2265. { TARGET_O_TRUNC, TARGET_O_TRUNC, O_TRUNC, O_TRUNC, },
  2266. { TARGET_O_APPEND, TARGET_O_APPEND, O_APPEND, O_APPEND, },
  2267. { TARGET_O_NONBLOCK, TARGET_O_NONBLOCK, O_NONBLOCK, O_NONBLOCK, },
  2268. { TARGET_O_SYNC, TARGET_O_SYNC, O_SYNC, O_SYNC, },
  2269. { TARGET_FASYNC, TARGET_FASYNC, FASYNC, FASYNC, },
  2270. { TARGET_O_DIRECTORY, TARGET_O_DIRECTORY, O_DIRECTORY, O_DIRECTORY, },
  2271. { TARGET_O_NOFOLLOW, TARGET_O_NOFOLLOW, O_NOFOLLOW, O_NOFOLLOW, },
  2272. { TARGET_O_LARGEFILE, TARGET_O_LARGEFILE, O_LARGEFILE, O_LARGEFILE, },
  2273. #if defined(O_DIRECT)
  2274. { TARGET_O_DIRECT, TARGET_O_DIRECT, O_DIRECT, O_DIRECT, },
  2275. #endif
  2276. { 0, 0, 0, 0 }
  2277. };
  2278. #if defined(TARGET_I386)
  2279. /* NOTE: there is really one LDT for all the threads */
  2280. static uint8_t *ldt_table;
  2281. static abi_long read_ldt(abi_ulong ptr, unsigned long bytecount)
  2282. {
  2283. int size;
  2284. void *p;
  2285. if (!ldt_table)
  2286. return 0;
  2287. size = TARGET_LDT_ENTRIES * TARGET_LDT_ENTRY_SIZE;
  2288. if (size > bytecount)
  2289. size = bytecount;
  2290. p = lock_user(VERIFY_WRITE, ptr, size, 0);
  2291. if (!p)
  2292. return -TARGET_EFAULT;
  2293. /* ??? Should this by byteswapped? */
  2294. memcpy(p, ldt_table, size);
  2295. unlock_user(p, ptr, size);
  2296. return size;
  2297. }
  2298. /* XXX: add locking support */
  2299. static abi_long write_ldt(CPUX86State *env,
  2300. abi_ulong ptr, unsigned long bytecount, int oldmode)
  2301. {
  2302. struct target_modify_ldt_ldt_s ldt_info;
  2303. struct target_modify_ldt_ldt_s *target_ldt_info;
  2304. int seg_32bit, contents, read_exec_only, limit_in_pages;
  2305. int seg_not_present, useable, lm;
  2306. uint32_t *lp, entry_1, entry_2;
  2307. if (bytecount != sizeof(ldt_info))
  2308. return -TARGET_EINVAL;
  2309. if (!lock_user_struct(VERIFY_READ, target_ldt_info, ptr, 1))
  2310. return -TARGET_EFAULT;
  2311. ldt_info.entry_number = tswap32(target_ldt_info->entry_number);
  2312. ldt_info.base_addr = tswapl(target_ldt_info->base_addr);
  2313. ldt_info.limit = tswap32(target_ldt_info->limit);
  2314. ldt_info.flags = tswap32(target_ldt_info->flags);
  2315. unlock_user_struct(target_ldt_info, ptr, 0);
  2316. if (ldt_info.entry_number >= TARGET_LDT_ENTRIES)
  2317. return -TARGET_EINVAL;
  2318. seg_32bit = ldt_info.flags & 1;
  2319. contents = (ldt_info.flags >> 1) & 3;
  2320. read_exec_only = (ldt_info.flags >> 3) & 1;
  2321. limit_in_pages = (ldt_info.flags >> 4) & 1;
  2322. seg_not_present = (ldt_info.flags >> 5) & 1;
  2323. useable = (ldt_info.flags >> 6) & 1;
  2324. #ifdef TARGET_ABI32
  2325. lm = 0;
  2326. #else
  2327. lm = (ldt_info.flags >> 7) & 1;
  2328. #endif
  2329. if (contents == 3) {
  2330. if (oldmode)
  2331. return -TARGET_EINVAL;
  2332. if (seg_not_present == 0)
  2333. return -TARGET_EINVAL;
  2334. }
  2335. /* allocate the LDT */
  2336. if (!ldt_table) {
  2337. env->ldt.base = target_mmap(0,
  2338. TARGET_LDT_ENTRIES * TARGET_LDT_ENTRY_SIZE,
  2339. PROT_READ|PROT_WRITE,
  2340. MAP_ANONYMOUS|MAP_PRIVATE, -1, 0);
  2341. if (env->ldt.base == -1)
  2342. return -TARGET_ENOMEM;
  2343. memset(g2h(env->ldt.base), 0,
  2344. TARGET_LDT_ENTRIES * TARGET_LDT_ENTRY_SIZE);
  2345. env->ldt.limit = 0xffff;
  2346. ldt_table = g2h(env->ldt.base);
  2347. }
  2348. /* NOTE: same code as Linux kernel */
  2349. /* Allow LDTs to be cleared by the user. */
  2350. if (ldt_info.base_addr == 0 && ldt_info.limit == 0) {
  2351. if (oldmode ||
  2352. (contents == 0 &&
  2353. read_exec_only == 1 &&
  2354. seg_32bit == 0 &&
  2355. limit_in_pages == 0 &&
  2356. seg_not_present == 1 &&
  2357. useable == 0 )) {
  2358. entry_1 = 0;
  2359. entry_2 = 0;
  2360. goto install;
  2361. }
  2362. }
  2363. entry_1 = ((ldt_info.base_addr & 0x0000ffff) << 16) |
  2364. (ldt_info.limit & 0x0ffff);
  2365. entry_2 = (ldt_info.base_addr & 0xff000000) |
  2366. ((ldt_info.base_addr & 0x00ff0000) >> 16) |
  2367. (ldt_info.limit & 0xf0000) |
  2368. ((read_exec_only ^ 1) << 9) |
  2369. (contents << 10) |
  2370. ((seg_not_present ^ 1) << 15) |
  2371. (seg_32bit << 22) |
  2372. (limit_in_pages << 23) |
  2373. (lm << 21) |
  2374. 0x7000;
  2375. if (!oldmode)
  2376. entry_2 |= (useable << 20);
  2377. /* Install the new entry ... */
  2378. install:
  2379. lp = (uint32_t *)(ldt_table + (ldt_info.entry_number << 3));
  2380. lp[0] = tswap32(entry_1);
  2381. lp[1] = tswap32(entry_2);
  2382. return 0;
  2383. }
  2384. /* specific and weird i386 syscalls */
  2385. static abi_long do_modify_ldt(CPUX86State *env, int func, abi_ulong ptr,
  2386. unsigned long bytecount)
  2387. {
  2388. abi_long ret;
  2389. switch (func) {
  2390. case 0:
  2391. ret = read_ldt(ptr, bytecount);
  2392. break;
  2393. case 1:
  2394. ret = write_ldt(env, ptr, bytecount, 1);
  2395. break;
  2396. case 0x11:
  2397. ret = write_ldt(env, ptr, bytecount, 0);
  2398. break;
  2399. default:
  2400. ret = -TARGET_ENOSYS;
  2401. break;
  2402. }
  2403. return ret;
  2404. }
  2405. #if defined(TARGET_I386) && defined(TARGET_ABI32)
  2406. static abi_long do_set_thread_area(CPUX86State *env, abi_ulong ptr)
  2407. {
  2408. uint64_t *gdt_table = g2h(env->gdt.base);
  2409. struct target_modify_ldt_ldt_s ldt_info;
  2410. struct target_modify_ldt_ldt_s *target_ldt_info;
  2411. int seg_32bit, contents, read_exec_only, limit_in_pages;
  2412. int seg_not_present, useable, lm;
  2413. uint32_t *lp, entry_1, entry_2;
  2414. int i;
  2415. lock_user_struct(VERIFY_WRITE, target_ldt_info, ptr, 1);
  2416. if (!target_ldt_info)
  2417. return -TARGET_EFAULT;
  2418. ldt_info.entry_number = tswap32(target_ldt_info->entry_number);
  2419. ldt_info.base_addr = tswapl(target_ldt_info->base_addr);
  2420. ldt_info.limit = tswap32(target_ldt_info->limit);
  2421. ldt_info.flags = tswap32(target_ldt_info->flags);
  2422. if (ldt_info.entry_number == -1) {
  2423. for (i=TARGET_GDT_ENTRY_TLS_MIN; i<=TARGET_GDT_ENTRY_TLS_MAX; i++) {
  2424. if (gdt_table[i] == 0) {
  2425. ldt_info.entry_number = i;
  2426. target_ldt_info->entry_number = tswap32(i);
  2427. break;
  2428. }
  2429. }
  2430. }
  2431. unlock_user_struct(target_ldt_info, ptr, 1);
  2432. if (ldt_info.entry_number < TARGET_GDT_ENTRY_TLS_MIN ||
  2433. ldt_info.entry_number > TARGET_GDT_ENTRY_TLS_MAX)
  2434. return -TARGET_EINVAL;
  2435. seg_32bit = ldt_info.flags & 1;
  2436. contents = (ldt_info.flags >> 1) & 3;
  2437. read_exec_only = (ldt_info.flags >> 3) & 1;
  2438. limit_in_pages = (ldt_info.flags >> 4) & 1;
  2439. seg_not_present = (ldt_info.flags >> 5) & 1;
  2440. useable = (ldt_info.flags >> 6) & 1;
  2441. #ifdef TARGET_ABI32
  2442. lm = 0;
  2443. #else
  2444. lm = (ldt_info.flags >> 7) & 1;
  2445. #endif
  2446. if (contents == 3) {
  2447. if (seg_not_present == 0)
  2448. return -TARGET_EINVAL;
  2449. }
  2450. /* NOTE: same code as Linux kernel */
  2451. /* Allow LDTs to be cleared by the user. */
  2452. if (ldt_info.base_addr == 0 && ldt_info.limit == 0) {
  2453. if ((contents == 0 &&
  2454. read_exec_only == 1 &&
  2455. seg_32bit == 0 &&
  2456. limit_in_pages == 0 &&
  2457. seg_not_present == 1 &&
  2458. useable == 0 )) {
  2459. entry_1 = 0;
  2460. entry_2 = 0;
  2461. goto install;
  2462. }
  2463. }
  2464. entry_1 = ((ldt_info.base_addr & 0x0000ffff) << 16) |
  2465. (ldt_info.limit & 0x0ffff);
  2466. entry_2 = (ldt_info.base_addr & 0xff000000) |
  2467. ((ldt_info.base_addr & 0x00ff0000) >> 16) |
  2468. (ldt_info.limit & 0xf0000) |
  2469. ((read_exec_only ^ 1) << 9) |
  2470. (contents << 10) |
  2471. ((seg_not_present ^ 1) << 15) |
  2472. (seg_32bit << 22) |
  2473. (limit_in_pages << 23) |
  2474. (useable << 20) |
  2475. (lm << 21) |
  2476. 0x7000;
  2477. /* Install the new entry ... */
  2478. install:
  2479. lp = (uint32_t *)(gdt_table + ldt_info.entry_number);
  2480. lp[0] = tswap32(entry_1);
  2481. lp[1] = tswap32(entry_2);
  2482. return 0;
  2483. }
  2484. static abi_long do_get_thread_area(CPUX86State *env, abi_ulong ptr)
  2485. {
  2486. struct target_modify_ldt_ldt_s *target_ldt_info;
  2487. uint64_t *gdt_table = g2h(env->gdt.base);
  2488. uint32_t base_addr, limit, flags;
  2489. int seg_32bit, contents, read_exec_only, limit_in_pages, idx;
  2490. int seg_not_present, useable, lm;
  2491. uint32_t *lp, entry_1, entry_2;
  2492. lock_user_struct(VERIFY_WRITE, target_ldt_info, ptr, 1);
  2493. if (!target_ldt_info)
  2494. return -TARGET_EFAULT;
  2495. idx = tswap32(target_ldt_info->entry_number);
  2496. if (idx < TARGET_GDT_ENTRY_TLS_MIN ||
  2497. idx > TARGET_GDT_ENTRY_TLS_MAX) {
  2498. unlock_user_struct(target_ldt_info, ptr, 1);
  2499. return -TARGET_EINVAL;
  2500. }
  2501. lp = (uint32_t *)(gdt_table + idx);
  2502. entry_1 = tswap32(lp[0]);
  2503. entry_2 = tswap32(lp[1]);
  2504. read_exec_only = ((entry_2 >> 9) & 1) ^ 1;
  2505. contents = (entry_2 >> 10) & 3;
  2506. seg_not_present = ((entry_2 >> 15) & 1) ^ 1;
  2507. seg_32bit = (entry_2 >> 22) & 1;
  2508. limit_in_pages = (entry_2 >> 23) & 1;
  2509. useable = (entry_2 >> 20) & 1;
  2510. #ifdef TARGET_ABI32
  2511. lm = 0;
  2512. #else
  2513. lm = (entry_2 >> 21) & 1;
  2514. #endif
  2515. flags = (seg_32bit << 0) | (contents << 1) |
  2516. (read_exec_only << 3) | (limit_in_pages << 4) |
  2517. (seg_not_present << 5) | (useable << 6) | (lm << 7);
  2518. limit = (entry_1 & 0xffff) | (entry_2 & 0xf0000);
  2519. base_addr = (entry_1 >> 16) |
  2520. (entry_2 & 0xff000000) |
  2521. ((entry_2 & 0xff) << 16);
  2522. target_ldt_info->base_addr = tswapl(base_addr);
  2523. target_ldt_info->limit = tswap32(limit);
  2524. target_ldt_info->flags = tswap32(flags);
  2525. unlock_user_struct(target_ldt_info, ptr, 1);
  2526. return 0;
  2527. }
  2528. #endif /* TARGET_I386 && TARGET_ABI32 */
  2529. #ifndef TARGET_ABI32
  2530. static abi_long do_arch_prctl(CPUX86State *env, int code, abi_ulong addr)
  2531. {
  2532. abi_long ret;
  2533. abi_ulong val;
  2534. int idx;
  2535. switch(code) {
  2536. case TARGET_ARCH_SET_GS:
  2537. case TARGET_ARCH_SET_FS:
  2538. if (code == TARGET_ARCH_SET_GS)
  2539. idx = R_GS;
  2540. else
  2541. idx = R_FS;
  2542. cpu_x86_load_seg(env, idx, 0);
  2543. env->segs[idx].base = addr;
  2544. break;
  2545. case TARGET_ARCH_GET_GS:
  2546. case TARGET_ARCH_GET_FS:
  2547. if (code == TARGET_ARCH_GET_GS)
  2548. idx = R_GS;
  2549. else
  2550. idx = R_FS;
  2551. val = env->segs[idx].base;
  2552. if (put_user(val, addr, abi_ulong))
  2553. return -TARGET_EFAULT;
  2554. break;
  2555. default:
  2556. ret = -TARGET_EINVAL;
  2557. break;
  2558. }
  2559. return 0;
  2560. }
  2561. #endif
  2562. #endif /* defined(TARGET_I386) */
  2563. #if defined(USE_NPTL)
  2564. #define NEW_STACK_SIZE PTHREAD_STACK_MIN
  2565. static pthread_mutex_t clone_lock = PTHREAD_MUTEX_INITIALIZER;
  2566. typedef struct {
  2567. CPUState *env;
  2568. pthread_mutex_t mutex;
  2569. pthread_cond_t cond;
  2570. pthread_t thread;
  2571. uint32_t tid;
  2572. abi_ulong child_tidptr;
  2573. abi_ulong parent_tidptr;
  2574. sigset_t sigmask;
  2575. } new_thread_info;
  2576. static void *clone_func(void *arg)
  2577. {
  2578. new_thread_info *info = arg;
  2579. CPUState *env;
  2580. env = info->env;
  2581. thread_env = env;
  2582. info->tid = gettid();
  2583. if (info->child_tidptr)
  2584. put_user_u32(info->tid, info->child_tidptr);
  2585. if (info->parent_tidptr)
  2586. put_user_u32(info->tid, info->parent_tidptr);
  2587. /* Enable signals. */
  2588. sigprocmask(SIG_SETMASK, &info->sigmask, NULL);
  2589. /* Signal to the parent that we're ready. */
  2590. pthread_mutex_lock(&info->mutex);
  2591. pthread_cond_broadcast(&info->cond);
  2592. pthread_mutex_unlock(&info->mutex);
  2593. /* Wait until the parent has finshed initializing the tls state. */
  2594. pthread_mutex_lock(&clone_lock);
  2595. pthread_mutex_unlock(&clone_lock);
  2596. cpu_loop(env);
  2597. /* never exits */
  2598. return NULL;
  2599. }
  2600. #else
  2601. /* this stack is the equivalent of the kernel stack associated with a
  2602. thread/process */
  2603. #define NEW_STACK_SIZE 8192
  2604. static int clone_func(void *arg)
  2605. {
  2606. CPUState *env = arg;
  2607. cpu_loop(env);
  2608. /* never exits */
  2609. return 0;
  2610. }
  2611. #endif
  2612. /* do_fork() Must return host values and target errnos (unlike most
  2613. do_*() functions). */
  2614. static int do_fork(CPUState *env, unsigned int flags, abi_ulong newsp,
  2615. abi_ulong parent_tidptr, target_ulong newtls,
  2616. abi_ulong child_tidptr)
  2617. {
  2618. int ret;
  2619. TaskState *ts;
  2620. uint8_t *new_stack;
  2621. CPUState *new_env;
  2622. #if defined(USE_NPTL)
  2623. unsigned int nptl_flags;
  2624. sigset_t sigmask;
  2625. #endif
  2626. /* Emulate vfork() with fork() */
  2627. if (flags & CLONE_VFORK)
  2628. flags &= ~(CLONE_VFORK | CLONE_VM);
  2629. if (flags & CLONE_VM) {
  2630. #if defined(USE_NPTL)
  2631. new_thread_info info;
  2632. pthread_attr_t attr;
  2633. #endif
  2634. ts = qemu_mallocz(sizeof(TaskState) + NEW_STACK_SIZE);
  2635. init_task_state(ts);
  2636. new_stack = ts->stack;
  2637. /* we create a new CPU instance. */
  2638. new_env = cpu_copy(env);
  2639. /* Init regs that differ from the parent. */
  2640. cpu_clone_regs(new_env, newsp);
  2641. new_env->opaque = ts;
  2642. #if defined(USE_NPTL)
  2643. nptl_flags = flags;
  2644. flags &= ~CLONE_NPTL_FLAGS2;
  2645. /* TODO: Implement CLONE_CHILD_CLEARTID. */
  2646. if (nptl_flags & CLONE_SETTLS)
  2647. cpu_set_tls (new_env, newtls);
  2648. /* Grab a mutex so that thread setup appears atomic. */
  2649. pthread_mutex_lock(&clone_lock);
  2650. memset(&info, 0, sizeof(info));
  2651. pthread_mutex_init(&info.mutex, NULL);
  2652. pthread_mutex_lock(&info.mutex);
  2653. pthread_cond_init(&info.cond, NULL);
  2654. info.env = new_env;
  2655. if (nptl_flags & CLONE_CHILD_SETTID)
  2656. info.child_tidptr = child_tidptr;
  2657. if (nptl_flags & CLONE_PARENT_SETTID)
  2658. info.parent_tidptr = parent_tidptr;
  2659. ret = pthread_attr_init(&attr);
  2660. ret = pthread_attr_setstack(&attr, new_stack, NEW_STACK_SIZE);
  2661. /* It is not safe to deliver signals until the child has finished
  2662. initializing, so temporarily block all signals. */
  2663. sigfillset(&sigmask);
  2664. sigprocmask(SIG_BLOCK, &sigmask, &info.sigmask);
  2665. ret = pthread_create(&info.thread, &attr, clone_func, &info);
  2666. sigprocmask(SIG_SETMASK, &info.sigmask, NULL);
  2667. pthread_attr_destroy(&attr);
  2668. if (ret == 0) {
  2669. /* Wait for the child to initialize. */
  2670. pthread_cond_wait(&info.cond, &info.mutex);
  2671. ret = info.tid;
  2672. if (flags & CLONE_PARENT_SETTID)
  2673. put_user_u32(ret, parent_tidptr);
  2674. } else {
  2675. ret = -1;
  2676. }
  2677. pthread_mutex_unlock(&info.mutex);
  2678. pthread_cond_destroy(&info.cond);
  2679. pthread_mutex_destroy(&info.mutex);
  2680. pthread_mutex_unlock(&clone_lock);
  2681. #else
  2682. if (flags & CLONE_NPTL_FLAGS2)
  2683. return -EINVAL;
  2684. /* This is probably going to die very quickly, but do it anyway. */
  2685. #ifdef __ia64__
  2686. ret = __clone2(clone_func, new_stack + NEW_STACK_SIZE, flags, new_env);
  2687. #else
  2688. ret = clone(clone_func, new_stack + NEW_STACK_SIZE, flags, new_env);
  2689. #endif
  2690. #endif
  2691. } else {
  2692. /* if no CLONE_VM, we consider it is a fork */
  2693. if ((flags & ~(CSIGNAL | CLONE_NPTL_FLAGS2)) != 0)
  2694. return -EINVAL;
  2695. fork_start();
  2696. ret = fork();
  2697. if (ret == 0) {
  2698. /* Child Process. */
  2699. cpu_clone_regs(env, newsp);
  2700. fork_end(1);
  2701. #if defined(USE_NPTL)
  2702. /* There is a race condition here. The parent process could
  2703. theoretically read the TID in the child process before the child
  2704. tid is set. This would require using either ptrace
  2705. (not implemented) or having *_tidptr to point at a shared memory
  2706. mapping. We can't repeat the spinlock hack used above because
  2707. the child process gets its own copy of the lock. */
  2708. if (flags & CLONE_CHILD_SETTID)
  2709. put_user_u32(gettid(), child_tidptr);
  2710. if (flags & CLONE_PARENT_SETTID)
  2711. put_user_u32(gettid(), parent_tidptr);
  2712. ts = (TaskState *)env->opaque;
  2713. if (flags & CLONE_SETTLS)
  2714. cpu_set_tls (env, newtls);
  2715. /* TODO: Implement CLONE_CHILD_CLEARTID. */
  2716. #endif
  2717. } else {
  2718. fork_end(0);
  2719. }
  2720. }
  2721. return ret;
  2722. }
  2723. static abi_long do_fcntl(int fd, int cmd, abi_ulong arg)
  2724. {
  2725. struct flock fl;
  2726. struct target_flock *target_fl;
  2727. struct flock64 fl64;
  2728. struct target_flock64 *target_fl64;
  2729. abi_long ret;
  2730. switch(cmd) {
  2731. case TARGET_F_GETLK:
  2732. if (!lock_user_struct(VERIFY_READ, target_fl, arg, 1))
  2733. return -TARGET_EFAULT;
  2734. fl.l_type = tswap16(target_fl->l_type);
  2735. fl.l_whence = tswap16(target_fl->l_whence);
  2736. fl.l_start = tswapl(target_fl->l_start);
  2737. fl.l_len = tswapl(target_fl->l_len);
  2738. fl.l_pid = tswapl(target_fl->l_pid);
  2739. unlock_user_struct(target_fl, arg, 0);
  2740. ret = get_errno(fcntl(fd, cmd, &fl));
  2741. if (ret == 0) {
  2742. if (!lock_user_struct(VERIFY_WRITE, target_fl, arg, 0))
  2743. return -TARGET_EFAULT;
  2744. target_fl->l_type = tswap16(fl.l_type);
  2745. target_fl->l_whence = tswap16(fl.l_whence);
  2746. target_fl->l_start = tswapl(fl.l_start);
  2747. target_fl->l_len = tswapl(fl.l_len);
  2748. target_fl->l_pid = tswapl(fl.l_pid);
  2749. unlock_user_struct(target_fl, arg, 1);
  2750. }
  2751. break;
  2752. case TARGET_F_SETLK:
  2753. case TARGET_F_SETLKW:
  2754. if (!lock_user_struct(VERIFY_READ, target_fl, arg, 1))
  2755. return -TARGET_EFAULT;
  2756. fl.l_type = tswap16(target_fl->l_type);
  2757. fl.l_whence = tswap16(target_fl->l_whence);
  2758. fl.l_start = tswapl(target_fl->l_start);
  2759. fl.l_len = tswapl(target_fl->l_len);
  2760. fl.l_pid = tswapl(target_fl->l_pid);
  2761. unlock_user_struct(target_fl, arg, 0);
  2762. ret = get_errno(fcntl(fd, cmd, &fl));
  2763. break;
  2764. case TARGET_F_GETLK64:
  2765. if (!lock_user_struct(VERIFY_READ, target_fl64, arg, 1))
  2766. return -TARGET_EFAULT;
  2767. fl64.l_type = tswap16(target_fl64->l_type) >> 1;
  2768. fl64.l_whence = tswap16(target_fl64->l_whence);
  2769. fl64.l_start = tswapl(target_fl64->l_start);
  2770. fl64.l_len = tswapl(target_fl64->l_len);
  2771. fl64.l_pid = tswap16(target_fl64->l_pid);
  2772. unlock_user_struct(target_fl64, arg, 0);
  2773. ret = get_errno(fcntl(fd, cmd >> 1, &fl64));
  2774. if (ret == 0) {
  2775. if (!lock_user_struct(VERIFY_WRITE, target_fl64, arg, 0))
  2776. return -TARGET_EFAULT;
  2777. target_fl64->l_type = tswap16(fl64.l_type) >> 1;
  2778. target_fl64->l_whence = tswap16(fl64.l_whence);
  2779. target_fl64->l_start = tswapl(fl64.l_start);
  2780. target_fl64->l_len = tswapl(fl64.l_len);
  2781. target_fl64->l_pid = tswapl(fl64.l_pid);
  2782. unlock_user_struct(target_fl64, arg, 1);
  2783. }
  2784. break;
  2785. case TARGET_F_SETLK64:
  2786. case TARGET_F_SETLKW64:
  2787. if (!lock_user_struct(VERIFY_READ, target_fl64, arg, 1))
  2788. return -TARGET_EFAULT;
  2789. fl64.l_type = tswap16(target_fl64->l_type) >> 1;
  2790. fl64.l_whence = tswap16(target_fl64->l_whence);
  2791. fl64.l_start = tswapl(target_fl64->l_start);
  2792. fl64.l_len = tswapl(target_fl64->l_len);
  2793. fl64.l_pid = tswap16(target_fl64->l_pid);
  2794. unlock_user_struct(target_fl64, arg, 0);
  2795. ret = get_errno(fcntl(fd, cmd >> 1, &fl64));
  2796. break;
  2797. case F_GETFL:
  2798. ret = get_errno(fcntl(fd, cmd, arg));
  2799. if (ret >= 0) {
  2800. ret = host_to_target_bitmask(ret, fcntl_flags_tbl);
  2801. }
  2802. break;
  2803. case F_SETFL:
  2804. ret = get_errno(fcntl(fd, cmd, target_to_host_bitmask(arg, fcntl_flags_tbl)));
  2805. break;
  2806. default:
  2807. ret = get_errno(fcntl(fd, cmd, arg));
  2808. break;
  2809. }
  2810. return ret;
  2811. }
  2812. #ifdef USE_UID16
  2813. static inline int high2lowuid(int uid)
  2814. {
  2815. if (uid > 65535)
  2816. return 65534;
  2817. else
  2818. return uid;
  2819. }
  2820. static inline int high2lowgid(int gid)
  2821. {
  2822. if (gid > 65535)
  2823. return 65534;
  2824. else
  2825. return gid;
  2826. }
  2827. static inline int low2highuid(int uid)
  2828. {
  2829. if ((int16_t)uid == -1)
  2830. return -1;
  2831. else
  2832. return uid;
  2833. }
  2834. static inline int low2highgid(int gid)
  2835. {
  2836. if ((int16_t)gid == -1)
  2837. return -1;
  2838. else
  2839. return gid;
  2840. }
  2841. #endif /* USE_UID16 */
  2842. void syscall_init(void)
  2843. {
  2844. IOCTLEntry *ie;
  2845. const argtype *arg_type;
  2846. int size;
  2847. int i;
  2848. #define STRUCT(name, list...) thunk_register_struct(STRUCT_ ## name, #name, struct_ ## name ## _def);
  2849. #define STRUCT_SPECIAL(name) thunk_register_struct_direct(STRUCT_ ## name, #name, &struct_ ## name ## _def);
  2850. #include "syscall_types.h"
  2851. #undef STRUCT
  2852. #undef STRUCT_SPECIAL
  2853. /* we patch the ioctl size if necessary. We rely on the fact that
  2854. no ioctl has all the bits at '1' in the size field */
  2855. ie = ioctl_entries;
  2856. while (ie->target_cmd != 0) {
  2857. if (((ie->target_cmd >> TARGET_IOC_SIZESHIFT) & TARGET_IOC_SIZEMASK) ==
  2858. TARGET_IOC_SIZEMASK) {
  2859. arg_type = ie->arg_type;
  2860. if (arg_type[0] != TYPE_PTR) {
  2861. fprintf(stderr, "cannot patch size for ioctl 0x%x\n",
  2862. ie->target_cmd);
  2863. exit(1);
  2864. }
  2865. arg_type++;
  2866. size = thunk_type_size(arg_type, 0);
  2867. ie->target_cmd = (ie->target_cmd &
  2868. ~(TARGET_IOC_SIZEMASK << TARGET_IOC_SIZESHIFT)) |
  2869. (size << TARGET_IOC_SIZESHIFT);
  2870. }
  2871. /* Build target_to_host_errno_table[] table from
  2872. * host_to_target_errno_table[]. */
  2873. for (i=0; i < ERRNO_TABLE_SIZE; i++)
  2874. target_to_host_errno_table[host_to_target_errno_table[i]] = i;
  2875. /* automatic consistency check if same arch */
  2876. #if (defined(__i386__) && defined(TARGET_I386) && defined(TARGET_ABI32)) || \
  2877. (defined(__x86_64__) && defined(TARGET_X86_64))
  2878. if (unlikely(ie->target_cmd != ie->host_cmd)) {
  2879. fprintf(stderr, "ERROR: ioctl(%s): target=0x%x host=0x%x\n",
  2880. ie->name, ie->target_cmd, ie->host_cmd);
  2881. }
  2882. #endif
  2883. ie++;
  2884. }
  2885. }
  2886. #if TARGET_ABI_BITS == 32
  2887. static inline uint64_t target_offset64(uint32_t word0, uint32_t word1)
  2888. {
  2889. #ifdef TARGET_WORDS_BIGENDIAN
  2890. return ((uint64_t)word0 << 32) | word1;
  2891. #else
  2892. return ((uint64_t)word1 << 32) | word0;
  2893. #endif
  2894. }
  2895. #else /* TARGET_ABI_BITS == 32 */
  2896. static inline uint64_t target_offset64(uint64_t word0, uint64_t word1)
  2897. {
  2898. return word0;
  2899. }
  2900. #endif /* TARGET_ABI_BITS != 32 */
  2901. #ifdef TARGET_NR_truncate64
  2902. static inline abi_long target_truncate64(void *cpu_env, const char *arg1,
  2903. abi_long arg2,
  2904. abi_long arg3,
  2905. abi_long arg4)
  2906. {
  2907. #ifdef TARGET_ARM
  2908. if (((CPUARMState *)cpu_env)->eabi)
  2909. {
  2910. arg2 = arg3;
  2911. arg3 = arg4;
  2912. }
  2913. #endif
  2914. return get_errno(truncate64(arg1, target_offset64(arg2, arg3)));
  2915. }
  2916. #endif
  2917. #ifdef TARGET_NR_ftruncate64
  2918. static inline abi_long target_ftruncate64(void *cpu_env, abi_long arg1,
  2919. abi_long arg2,
  2920. abi_long arg3,
  2921. abi_long arg4)
  2922. {
  2923. #ifdef TARGET_ARM
  2924. if (((CPUARMState *)cpu_env)->eabi)
  2925. {
  2926. arg2 = arg3;
  2927. arg3 = arg4;
  2928. }
  2929. #endif
  2930. return get_errno(ftruncate64(arg1, target_offset64(arg2, arg3)));
  2931. }
  2932. #endif
  2933. static inline abi_long target_to_host_timespec(struct timespec *host_ts,
  2934. abi_ulong target_addr)
  2935. {
  2936. struct target_timespec *target_ts;
  2937. if (!lock_user_struct(VERIFY_READ, target_ts, target_addr, 1))
  2938. return -TARGET_EFAULT;
  2939. host_ts->tv_sec = tswapl(target_ts->tv_sec);
  2940. host_ts->tv_nsec = tswapl(target_ts->tv_nsec);
  2941. unlock_user_struct(target_ts, target_addr, 0);
  2942. return 0;
  2943. }
  2944. static inline abi_long host_to_target_timespec(abi_ulong target_addr,
  2945. struct timespec *host_ts)
  2946. {
  2947. struct target_timespec *target_ts;
  2948. if (!lock_user_struct(VERIFY_WRITE, target_ts, target_addr, 0))
  2949. return -TARGET_EFAULT;
  2950. target_ts->tv_sec = tswapl(host_ts->tv_sec);
  2951. target_ts->tv_nsec = tswapl(host_ts->tv_nsec);
  2952. unlock_user_struct(target_ts, target_addr, 1);
  2953. return 0;
  2954. }
  2955. #ifdef TARGET_NR_stat64
  2956. static inline abi_long host_to_target_stat64(void *cpu_env,
  2957. abi_ulong target_addr,
  2958. struct stat *host_st)
  2959. {
  2960. #ifdef TARGET_ARM
  2961. if (((CPUARMState *)cpu_env)->eabi) {
  2962. struct target_eabi_stat64 *target_st;
  2963. if (!lock_user_struct(VERIFY_WRITE, target_st, target_addr, 0))
  2964. return -TARGET_EFAULT;
  2965. memset(target_st, 0, sizeof(struct target_eabi_stat64));
  2966. __put_user(host_st->st_dev, &target_st->st_dev);
  2967. __put_user(host_st->st_ino, &target_st->st_ino);
  2968. #ifdef TARGET_STAT64_HAS_BROKEN_ST_INO
  2969. __put_user(host_st->st_ino, &target_st->__st_ino);
  2970. #endif
  2971. __put_user(host_st->st_mode, &target_st->st_mode);
  2972. __put_user(host_st->st_nlink, &target_st->st_nlink);
  2973. __put_user(host_st->st_uid, &target_st->st_uid);
  2974. __put_user(host_st->st_gid, &target_st->st_gid);
  2975. __put_user(host_st->st_rdev, &target_st->st_rdev);
  2976. __put_user(host_st->st_size, &target_st->st_size);
  2977. __put_user(host_st->st_blksize, &target_st->st_blksize);
  2978. __put_user(host_st->st_blocks, &target_st->st_blocks);
  2979. __put_user(host_st->st_atime, &target_st->target_st_atime);
  2980. __put_user(host_st->st_mtime, &target_st->target_st_mtime);
  2981. __put_user(host_st->st_ctime, &target_st->target_st_ctime);
  2982. unlock_user_struct(target_st, target_addr, 1);
  2983. } else
  2984. #endif
  2985. {
  2986. struct target_stat64 *target_st;
  2987. if (!lock_user_struct(VERIFY_WRITE, target_st, target_addr, 0))
  2988. return -TARGET_EFAULT;
  2989. memset(target_st, 0, sizeof(struct target_stat64));
  2990. __put_user(host_st->st_dev, &target_st->st_dev);
  2991. __put_user(host_st->st_ino, &target_st->st_ino);
  2992. #ifdef TARGET_STAT64_HAS_BROKEN_ST_INO
  2993. __put_user(host_st->st_ino, &target_st->__st_ino);
  2994. #endif
  2995. __put_user(host_st->st_mode, &target_st->st_mode);
  2996. __put_user(host_st->st_nlink, &target_st->st_nlink);
  2997. __put_user(host_st->st_uid, &target_st->st_uid);
  2998. __put_user(host_st->st_gid, &target_st->st_gid);
  2999. __put_user(host_st->st_rdev, &target_st->st_rdev);
  3000. /* XXX: better use of kernel struct */
  3001. __put_user(host_st->st_size, &target_st->st_size);
  3002. __put_user(host_st->st_blksize, &target_st->st_blksize);
  3003. __put_user(host_st->st_blocks, &target_st->st_blocks);
  3004. __put_user(host_st->st_atime, &target_st->target_st_atime);
  3005. __put_user(host_st->st_mtime, &target_st->target_st_mtime);
  3006. __put_user(host_st->st_ctime, &target_st->target_st_ctime);
  3007. unlock_user_struct(target_st, target_addr, 1);
  3008. }
  3009. return 0;
  3010. }
  3011. #endif
  3012. #if defined(USE_NPTL)
  3013. /* ??? Using host futex calls even when target atomic operations
  3014. are not really atomic probably breaks things. However implementing
  3015. futexes locally would make futexes shared between multiple processes
  3016. tricky. However they're probably useless because guest atomic
  3017. operations won't work either. */
  3018. static int do_futex(target_ulong uaddr, int op, int val, target_ulong timeout,
  3019. target_ulong uaddr2, int val3)
  3020. {
  3021. struct timespec ts, *pts;
  3022. /* ??? We assume FUTEX_* constants are the same on both host
  3023. and target. */
  3024. switch (op) {
  3025. case FUTEX_WAIT:
  3026. if (timeout) {
  3027. pts = &ts;
  3028. target_to_host_timespec(pts, timeout);
  3029. } else {
  3030. pts = NULL;
  3031. }
  3032. return get_errno(sys_futex(g2h(uaddr), FUTEX_WAIT, tswap32(val),
  3033. pts, NULL, 0));
  3034. case FUTEX_WAKE:
  3035. return get_errno(sys_futex(g2h(uaddr), FUTEX_WAKE, val, NULL, NULL, 0));
  3036. case FUTEX_FD:
  3037. return get_errno(sys_futex(g2h(uaddr), FUTEX_FD, val, NULL, NULL, 0));
  3038. case FUTEX_REQUEUE:
  3039. return get_errno(sys_futex(g2h(uaddr), FUTEX_REQUEUE, val,
  3040. NULL, g2h(uaddr2), 0));
  3041. case FUTEX_CMP_REQUEUE:
  3042. return get_errno(sys_futex(g2h(uaddr), FUTEX_CMP_REQUEUE, val,
  3043. NULL, g2h(uaddr2), tswap32(val3)));
  3044. default:
  3045. return -TARGET_ENOSYS;
  3046. }
  3047. }
  3048. #endif
  3049. int get_osversion(void)
  3050. {
  3051. static int osversion;
  3052. struct new_utsname buf;
  3053. const char *s;
  3054. int i, n, tmp;
  3055. if (osversion)
  3056. return osversion;
  3057. if (qemu_uname_release && *qemu_uname_release) {
  3058. s = qemu_uname_release;
  3059. } else {
  3060. if (sys_uname(&buf))
  3061. return 0;
  3062. s = buf.release;
  3063. }
  3064. tmp = 0;
  3065. for (i = 0; i < 3; i++) {
  3066. n = 0;
  3067. while (*s >= '0' && *s <= '9') {
  3068. n *= 10;
  3069. n += *s - '0';
  3070. s++;
  3071. }
  3072. tmp = (tmp << 8) + n;
  3073. if (*s == '.')
  3074. s++;
  3075. }
  3076. osversion = tmp;
  3077. return osversion;
  3078. }
  3079. /* do_syscall() should always have a single exit point at the end so
  3080. that actions, such as logging of syscall results, can be performed.
  3081. All errnos that do_syscall() returns must be -TARGET_<errcode>. */
  3082. abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
  3083. abi_long arg2, abi_long arg3, abi_long arg4,
  3084. abi_long arg5, abi_long arg6)
  3085. {
  3086. abi_long ret;
  3087. struct stat st;
  3088. struct statfs stfs;
  3089. void *p;
  3090. #ifdef DEBUG
  3091. gemu_log("syscall %d", num);
  3092. #endif
  3093. if(do_strace)
  3094. print_syscall(num, arg1, arg2, arg3, arg4, arg5, arg6);
  3095. switch(num) {
  3096. case TARGET_NR_exit:
  3097. #ifdef HAVE_GPROF
  3098. _mcleanup();
  3099. #endif
  3100. gdb_exit(cpu_env, arg1);
  3101. /* XXX: should free thread stack and CPU env */
  3102. sys_exit(arg1);
  3103. ret = 0; /* avoid warning */
  3104. break;
  3105. case TARGET_NR_read:
  3106. if (arg3 == 0)
  3107. ret = 0;
  3108. else {
  3109. if (!(p = lock_user(VERIFY_WRITE, arg2, arg3, 0)))
  3110. goto efault;
  3111. ret = get_errno(read(arg1, p, arg3));
  3112. unlock_user(p, arg2, ret);
  3113. }
  3114. break;
  3115. case TARGET_NR_write:
  3116. if (!(p = lock_user(VERIFY_READ, arg2, arg3, 1)))
  3117. goto efault;
  3118. ret = get_errno(write(arg1, p, arg3));
  3119. unlock_user(p, arg2, 0);
  3120. break;
  3121. case TARGET_NR_open:
  3122. if (!(p = lock_user_string(arg1)))
  3123. goto efault;
  3124. ret = get_errno(open(path(p),
  3125. target_to_host_bitmask(arg2, fcntl_flags_tbl),
  3126. arg3));
  3127. unlock_user(p, arg1, 0);
  3128. break;
  3129. #if defined(TARGET_NR_openat) && defined(__NR_openat)
  3130. case TARGET_NR_openat:
  3131. if (!(p = lock_user_string(arg2)))
  3132. goto efault;
  3133. ret = get_errno(sys_openat(arg1,
  3134. path(p),
  3135. target_to_host_bitmask(arg3, fcntl_flags_tbl),
  3136. arg4));
  3137. unlock_user(p, arg2, 0);
  3138. break;
  3139. #endif
  3140. case TARGET_NR_close:
  3141. ret = get_errno(close(arg1));
  3142. break;
  3143. case TARGET_NR_brk:
  3144. ret = do_brk(arg1);
  3145. break;
  3146. case TARGET_NR_fork:
  3147. ret = get_errno(do_fork(cpu_env, SIGCHLD, 0, 0, 0, 0));
  3148. break;
  3149. #ifdef TARGET_NR_waitpid
  3150. case TARGET_NR_waitpid:
  3151. {
  3152. int status;
  3153. ret = get_errno(waitpid(arg1, &status, arg3));
  3154. if (!is_error(ret) && arg2
  3155. && put_user_s32(status, arg2))
  3156. goto efault;
  3157. }
  3158. break;
  3159. #endif
  3160. #ifdef TARGET_NR_waitid
  3161. case TARGET_NR_waitid:
  3162. {
  3163. siginfo_t info;
  3164. info.si_pid = 0;
  3165. ret = get_errno(waitid(arg1, arg2, &info, arg4));
  3166. if (!is_error(ret) && arg3 && info.si_pid != 0) {
  3167. if (!(p = lock_user(VERIFY_WRITE, arg3, sizeof(target_siginfo_t), 0)))
  3168. goto efault;
  3169. host_to_target_siginfo(p, &info);
  3170. unlock_user(p, arg3, sizeof(target_siginfo_t));
  3171. }
  3172. }
  3173. break;
  3174. #endif
  3175. #ifdef TARGET_NR_creat /* not on alpha */
  3176. case TARGET_NR_creat:
  3177. if (!(p = lock_user_string(arg1)))
  3178. goto efault;
  3179. ret = get_errno(creat(p, arg2));
  3180. unlock_user(p, arg1, 0);
  3181. break;
  3182. #endif
  3183. case TARGET_NR_link:
  3184. {
  3185. void * p2;
  3186. p = lock_user_string(arg1);
  3187. p2 = lock_user_string(arg2);
  3188. if (!p || !p2)
  3189. ret = -TARGET_EFAULT;
  3190. else
  3191. ret = get_errno(link(p, p2));
  3192. unlock_user(p2, arg2, 0);
  3193. unlock_user(p, arg1, 0);
  3194. }
  3195. break;
  3196. #if defined(TARGET_NR_linkat) && defined(__NR_linkat)
  3197. case TARGET_NR_linkat:
  3198. {
  3199. void * p2 = NULL;
  3200. if (!arg2 || !arg4)
  3201. goto efault;
  3202. p = lock_user_string(arg2);
  3203. p2 = lock_user_string(arg4);
  3204. if (!p || !p2)
  3205. ret = -TARGET_EFAULT;
  3206. else
  3207. ret = get_errno(sys_linkat(arg1, p, arg3, p2, arg5));
  3208. unlock_user(p, arg2, 0);
  3209. unlock_user(p2, arg4, 0);
  3210. }
  3211. break;
  3212. #endif
  3213. case TARGET_NR_unlink:
  3214. if (!(p = lock_user_string(arg1)))
  3215. goto efault;
  3216. ret = get_errno(unlink(p));
  3217. unlock_user(p, arg1, 0);
  3218. break;
  3219. #if defined(TARGET_NR_unlinkat) && defined(__NR_unlinkat)
  3220. case TARGET_NR_unlinkat:
  3221. if (!(p = lock_user_string(arg2)))
  3222. goto efault;
  3223. ret = get_errno(sys_unlinkat(arg1, p, arg3));
  3224. unlock_user(p, arg2, 0);
  3225. break;
  3226. #endif
  3227. case TARGET_NR_execve:
  3228. {
  3229. char **argp, **envp;
  3230. int argc, envc;
  3231. abi_ulong gp;
  3232. abi_ulong guest_argp;
  3233. abi_ulong guest_envp;
  3234. abi_ulong addr;
  3235. char **q;
  3236. argc = 0;
  3237. guest_argp = arg2;
  3238. for (gp = guest_argp; gp; gp += sizeof(abi_ulong)) {
  3239. if (get_user_ual(addr, gp))
  3240. goto efault;
  3241. if (!addr)
  3242. break;
  3243. argc++;
  3244. }
  3245. envc = 0;
  3246. guest_envp = arg3;
  3247. for (gp = guest_envp; gp; gp += sizeof(abi_ulong)) {
  3248. if (get_user_ual(addr, gp))
  3249. goto efault;
  3250. if (!addr)
  3251. break;
  3252. envc++;
  3253. }
  3254. argp = alloca((argc + 1) * sizeof(void *));
  3255. envp = alloca((envc + 1) * sizeof(void *));
  3256. for (gp = guest_argp, q = argp; gp;
  3257. gp += sizeof(abi_ulong), q++) {
  3258. if (get_user_ual(addr, gp))
  3259. goto execve_efault;
  3260. if (!addr)
  3261. break;
  3262. if (!(*q = lock_user_string(addr)))
  3263. goto execve_efault;
  3264. }
  3265. *q = NULL;
  3266. for (gp = guest_envp, q = envp; gp;
  3267. gp += sizeof(abi_ulong), q++) {
  3268. if (get_user_ual(addr, gp))
  3269. goto execve_efault;
  3270. if (!addr)
  3271. break;
  3272. if (!(*q = lock_user_string(addr)))
  3273. goto execve_efault;
  3274. }
  3275. *q = NULL;
  3276. if (!(p = lock_user_string(arg1)))
  3277. goto execve_efault;
  3278. ret = get_errno(execve(p, argp, envp));
  3279. unlock_user(p, arg1, 0);
  3280. goto execve_end;
  3281. execve_efault:
  3282. ret = -TARGET_EFAULT;
  3283. execve_end:
  3284. for (gp = guest_argp, q = argp; *q;
  3285. gp += sizeof(abi_ulong), q++) {
  3286. if (get_user_ual(addr, gp)
  3287. || !addr)
  3288. break;
  3289. unlock_user(*q, addr, 0);
  3290. }
  3291. for (gp = guest_envp, q = envp; *q;
  3292. gp += sizeof(abi_ulong), q++) {
  3293. if (get_user_ual(addr, gp)
  3294. || !addr)
  3295. break;
  3296. unlock_user(*q, addr, 0);
  3297. }
  3298. }
  3299. break;
  3300. case TARGET_NR_chdir:
  3301. if (!(p = lock_user_string(arg1)))
  3302. goto efault;
  3303. ret = get_errno(chdir(p));
  3304. unlock_user(p, arg1, 0);
  3305. break;
  3306. #ifdef TARGET_NR_time
  3307. case TARGET_NR_time:
  3308. {
  3309. time_t host_time;
  3310. ret = get_errno(time(&host_time));
  3311. if (!is_error(ret)
  3312. && arg1
  3313. && put_user_sal(host_time, arg1))
  3314. goto efault;
  3315. }
  3316. break;
  3317. #endif
  3318. case TARGET_NR_mknod:
  3319. if (!(p = lock_user_string(arg1)))
  3320. goto efault;
  3321. ret = get_errno(mknod(p, arg2, arg3));
  3322. unlock_user(p, arg1, 0);
  3323. break;
  3324. #if defined(TARGET_NR_mknodat) && defined(__NR_mknodat)
  3325. case TARGET_NR_mknodat:
  3326. if (!(p = lock_user_string(arg2)))
  3327. goto efault;
  3328. ret = get_errno(sys_mknodat(arg1, p, arg3, arg4));
  3329. unlock_user(p, arg2, 0);
  3330. break;
  3331. #endif
  3332. case TARGET_NR_chmod:
  3333. if (!(p = lock_user_string(arg1)))
  3334. goto efault;
  3335. ret = get_errno(chmod(p, arg2));
  3336. unlock_user(p, arg1, 0);
  3337. break;
  3338. #ifdef TARGET_NR_break
  3339. case TARGET_NR_break:
  3340. goto unimplemented;
  3341. #endif
  3342. #ifdef TARGET_NR_oldstat
  3343. case TARGET_NR_oldstat:
  3344. goto unimplemented;
  3345. #endif
  3346. case TARGET_NR_lseek:
  3347. ret = get_errno(lseek(arg1, arg2, arg3));
  3348. break;
  3349. #ifdef TARGET_NR_getxpid
  3350. case TARGET_NR_getxpid:
  3351. #else
  3352. case TARGET_NR_getpid:
  3353. #endif
  3354. ret = get_errno(getpid());
  3355. break;
  3356. case TARGET_NR_mount:
  3357. {
  3358. /* need to look at the data field */
  3359. void *p2, *p3;
  3360. p = lock_user_string(arg1);
  3361. p2 = lock_user_string(arg2);
  3362. p3 = lock_user_string(arg3);
  3363. if (!p || !p2 || !p3)
  3364. ret = -TARGET_EFAULT;
  3365. else
  3366. /* FIXME - arg5 should be locked, but it isn't clear how to
  3367. * do that since it's not guaranteed to be a NULL-terminated
  3368. * string.
  3369. */
  3370. ret = get_errno(mount(p, p2, p3, (unsigned long)arg4, g2h(arg5)));
  3371. unlock_user(p, arg1, 0);
  3372. unlock_user(p2, arg2, 0);
  3373. unlock_user(p3, arg3, 0);
  3374. break;
  3375. }
  3376. #ifdef TARGET_NR_umount
  3377. case TARGET_NR_umount:
  3378. if (!(p = lock_user_string(arg1)))
  3379. goto efault;
  3380. ret = get_errno(umount(p));
  3381. unlock_user(p, arg1, 0);
  3382. break;
  3383. #endif
  3384. #ifdef TARGET_NR_stime /* not on alpha */
  3385. case TARGET_NR_stime:
  3386. {
  3387. time_t host_time;
  3388. if (get_user_sal(host_time, arg1))
  3389. goto efault;
  3390. ret = get_errno(stime(&host_time));
  3391. }
  3392. break;
  3393. #endif
  3394. case TARGET_NR_ptrace:
  3395. goto unimplemented;
  3396. #ifdef TARGET_NR_alarm /* not on alpha */
  3397. case TARGET_NR_alarm:
  3398. ret = alarm(arg1);
  3399. break;
  3400. #endif
  3401. #ifdef TARGET_NR_oldfstat
  3402. case TARGET_NR_oldfstat:
  3403. goto unimplemented;
  3404. #endif
  3405. #ifdef TARGET_NR_pause /* not on alpha */
  3406. case TARGET_NR_pause:
  3407. ret = get_errno(pause());
  3408. break;
  3409. #endif
  3410. #ifdef TARGET_NR_utime
  3411. case TARGET_NR_utime:
  3412. {
  3413. struct utimbuf tbuf, *host_tbuf;
  3414. struct target_utimbuf *target_tbuf;
  3415. if (arg2) {
  3416. if (!lock_user_struct(VERIFY_READ, target_tbuf, arg2, 1))
  3417. goto efault;
  3418. tbuf.actime = tswapl(target_tbuf->actime);
  3419. tbuf.modtime = tswapl(target_tbuf->modtime);
  3420. unlock_user_struct(target_tbuf, arg2, 0);
  3421. host_tbuf = &tbuf;
  3422. } else {
  3423. host_tbuf = NULL;
  3424. }
  3425. if (!(p = lock_user_string(arg1)))
  3426. goto efault;
  3427. ret = get_errno(utime(p, host_tbuf));
  3428. unlock_user(p, arg1, 0);
  3429. }
  3430. break;
  3431. #endif
  3432. case TARGET_NR_utimes:
  3433. {
  3434. struct timeval *tvp, tv[2];
  3435. if (arg2) {
  3436. if (copy_from_user_timeval(&tv[0], arg2)
  3437. || copy_from_user_timeval(&tv[1],
  3438. arg2 + sizeof(struct target_timeval)))
  3439. goto efault;
  3440. tvp = tv;
  3441. } else {
  3442. tvp = NULL;
  3443. }
  3444. if (!(p = lock_user_string(arg1)))
  3445. goto efault;
  3446. ret = get_errno(utimes(p, tvp));
  3447. unlock_user(p, arg1, 0);
  3448. }
  3449. break;
  3450. #if defined(TARGET_NR_futimesat) && defined(__NR_futimesat)
  3451. case TARGET_NR_futimesat:
  3452. {
  3453. struct timeval *tvp, tv[2];
  3454. if (arg3) {
  3455. if (copy_from_user_timeval(&tv[0], arg3)
  3456. || copy_from_user_timeval(&tv[1],
  3457. arg3 + sizeof(struct target_timeval)))
  3458. goto efault;
  3459. tvp = tv;
  3460. } else {
  3461. tvp = NULL;
  3462. }
  3463. if (!(p = lock_user_string(arg2)))
  3464. goto efault;
  3465. ret = get_errno(sys_futimesat(arg1, path(p), tvp));
  3466. unlock_user(p, arg2, 0);
  3467. }
  3468. break;
  3469. #endif
  3470. #ifdef TARGET_NR_stty
  3471. case TARGET_NR_stty:
  3472. goto unimplemented;
  3473. #endif
  3474. #ifdef TARGET_NR_gtty
  3475. case TARGET_NR_gtty:
  3476. goto unimplemented;
  3477. #endif
  3478. case TARGET_NR_access:
  3479. if (!(p = lock_user_string(arg1)))
  3480. goto efault;
  3481. ret = get_errno(access(p, arg2));
  3482. unlock_user(p, arg1, 0);
  3483. break;
  3484. #if defined(TARGET_NR_faccessat) && defined(__NR_faccessat)
  3485. case TARGET_NR_faccessat:
  3486. if (!(p = lock_user_string(arg2)))
  3487. goto efault;
  3488. ret = get_errno(sys_faccessat(arg1, p, arg3, arg4));
  3489. unlock_user(p, arg2, 0);
  3490. break;
  3491. #endif
  3492. #ifdef TARGET_NR_nice /* not on alpha */
  3493. case TARGET_NR_nice:
  3494. ret = get_errno(nice(arg1));
  3495. break;
  3496. #endif
  3497. #ifdef TARGET_NR_ftime
  3498. case TARGET_NR_ftime:
  3499. goto unimplemented;
  3500. #endif
  3501. case TARGET_NR_sync:
  3502. sync();
  3503. ret = 0;
  3504. break;
  3505. case TARGET_NR_kill:
  3506. ret = get_errno(kill(arg1, target_to_host_signal(arg2)));
  3507. break;
  3508. case TARGET_NR_rename:
  3509. {
  3510. void *p2;
  3511. p = lock_user_string(arg1);
  3512. p2 = lock_user_string(arg2);
  3513. if (!p || !p2)
  3514. ret = -TARGET_EFAULT;
  3515. else
  3516. ret = get_errno(rename(p, p2));
  3517. unlock_user(p2, arg2, 0);
  3518. unlock_user(p, arg1, 0);
  3519. }
  3520. break;
  3521. #if defined(TARGET_NR_renameat) && defined(__NR_renameat)
  3522. case TARGET_NR_renameat:
  3523. {
  3524. void *p2;
  3525. p = lock_user_string(arg2);
  3526. p2 = lock_user_string(arg4);
  3527. if (!p || !p2)
  3528. ret = -TARGET_EFAULT;
  3529. else
  3530. ret = get_errno(sys_renameat(arg1, p, arg3, p2));
  3531. unlock_user(p2, arg4, 0);
  3532. unlock_user(p, arg2, 0);
  3533. }
  3534. break;
  3535. #endif
  3536. case TARGET_NR_mkdir:
  3537. if (!(p = lock_user_string(arg1)))
  3538. goto efault;
  3539. ret = get_errno(mkdir(p, arg2));
  3540. unlock_user(p, arg1, 0);
  3541. break;
  3542. #if defined(TARGET_NR_mkdirat) && defined(__NR_mkdirat)
  3543. case TARGET_NR_mkdirat:
  3544. if (!(p = lock_user_string(arg2)))
  3545. goto efault;
  3546. ret = get_errno(sys_mkdirat(arg1, p, arg3));
  3547. unlock_user(p, arg2, 0);
  3548. break;
  3549. #endif
  3550. case TARGET_NR_rmdir:
  3551. if (!(p = lock_user_string(arg1)))
  3552. goto efault;
  3553. ret = get_errno(rmdir(p));
  3554. unlock_user(p, arg1, 0);
  3555. break;
  3556. case TARGET_NR_dup:
  3557. ret = get_errno(dup(arg1));
  3558. break;
  3559. case TARGET_NR_pipe:
  3560. {
  3561. int host_pipe[2];
  3562. ret = get_errno(pipe(host_pipe));
  3563. if (!is_error(ret)) {
  3564. #if defined(TARGET_MIPS)
  3565. CPUMIPSState *env = (CPUMIPSState*)cpu_env;
  3566. env->active_tc.gpr[3] = host_pipe[1];
  3567. ret = host_pipe[0];
  3568. #elif defined(TARGET_SH4)
  3569. ((CPUSH4State*)cpu_env)->gregs[1] = host_pipe[1];
  3570. ret = host_pipe[0];
  3571. #else
  3572. if (put_user_s32(host_pipe[0], arg1)
  3573. || put_user_s32(host_pipe[1], arg1 + sizeof(host_pipe[0])))
  3574. goto efault;
  3575. #endif
  3576. }
  3577. }
  3578. break;
  3579. case TARGET_NR_times:
  3580. {
  3581. struct target_tms *tmsp;
  3582. struct tms tms;
  3583. ret = get_errno(times(&tms));
  3584. if (arg1) {
  3585. tmsp = lock_user(VERIFY_WRITE, arg1, sizeof(struct target_tms), 0);
  3586. if (!tmsp)
  3587. goto efault;
  3588. tmsp->tms_utime = tswapl(host_to_target_clock_t(tms.tms_utime));
  3589. tmsp->tms_stime = tswapl(host_to_target_clock_t(tms.tms_stime));
  3590. tmsp->tms_cutime = tswapl(host_to_target_clock_t(tms.tms_cutime));
  3591. tmsp->tms_cstime = tswapl(host_to_target_clock_t(tms.tms_cstime));
  3592. }
  3593. if (!is_error(ret))
  3594. ret = host_to_target_clock_t(ret);
  3595. }
  3596. break;
  3597. #ifdef TARGET_NR_prof
  3598. case TARGET_NR_prof:
  3599. goto unimplemented;
  3600. #endif
  3601. #ifdef TARGET_NR_signal
  3602. case TARGET_NR_signal:
  3603. goto unimplemented;
  3604. #endif
  3605. case TARGET_NR_acct:
  3606. if (arg1 == 0) {
  3607. ret = get_errno(acct(NULL));
  3608. } else {
  3609. if (!(p = lock_user_string(arg1)))
  3610. goto efault;
  3611. ret = get_errno(acct(path(p)));
  3612. unlock_user(p, arg1, 0);
  3613. }
  3614. break;
  3615. #ifdef TARGET_NR_umount2 /* not on alpha */
  3616. case TARGET_NR_umount2:
  3617. if (!(p = lock_user_string(arg1)))
  3618. goto efault;
  3619. ret = get_errno(umount2(p, arg2));
  3620. unlock_user(p, arg1, 0);
  3621. break;
  3622. #endif
  3623. #ifdef TARGET_NR_lock
  3624. case TARGET_NR_lock:
  3625. goto unimplemented;
  3626. #endif
  3627. case TARGET_NR_ioctl:
  3628. ret = do_ioctl(arg1, arg2, arg3);
  3629. break;
  3630. case TARGET_NR_fcntl:
  3631. ret = do_fcntl(arg1, arg2, arg3);
  3632. break;
  3633. #ifdef TARGET_NR_mpx
  3634. case TARGET_NR_mpx:
  3635. goto unimplemented;
  3636. #endif
  3637. case TARGET_NR_setpgid:
  3638. ret = get_errno(setpgid(arg1, arg2));
  3639. break;
  3640. #ifdef TARGET_NR_ulimit
  3641. case TARGET_NR_ulimit:
  3642. goto unimplemented;
  3643. #endif
  3644. #ifdef TARGET_NR_oldolduname
  3645. case TARGET_NR_oldolduname:
  3646. goto unimplemented;
  3647. #endif
  3648. case TARGET_NR_umask:
  3649. ret = get_errno(umask(arg1));
  3650. break;
  3651. case TARGET_NR_chroot:
  3652. if (!(p = lock_user_string(arg1)))
  3653. goto efault;
  3654. ret = get_errno(chroot(p));
  3655. unlock_user(p, arg1, 0);
  3656. break;
  3657. case TARGET_NR_ustat:
  3658. goto unimplemented;
  3659. case TARGET_NR_dup2:
  3660. ret = get_errno(dup2(arg1, arg2));
  3661. break;
  3662. #ifdef TARGET_NR_getppid /* not on alpha */
  3663. case TARGET_NR_getppid:
  3664. ret = get_errno(getppid());
  3665. break;
  3666. #endif
  3667. case TARGET_NR_getpgrp:
  3668. ret = get_errno(getpgrp());
  3669. break;
  3670. case TARGET_NR_setsid:
  3671. ret = get_errno(setsid());
  3672. break;
  3673. #ifdef TARGET_NR_sigaction
  3674. case TARGET_NR_sigaction:
  3675. {
  3676. #if !defined(TARGET_MIPS)
  3677. struct target_old_sigaction *old_act;
  3678. struct target_sigaction act, oact, *pact;
  3679. if (arg2) {
  3680. if (!lock_user_struct(VERIFY_READ, old_act, arg2, 1))
  3681. goto efault;
  3682. act._sa_handler = old_act->_sa_handler;
  3683. target_siginitset(&act.sa_mask, old_act->sa_mask);
  3684. act.sa_flags = old_act->sa_flags;
  3685. act.sa_restorer = old_act->sa_restorer;
  3686. unlock_user_struct(old_act, arg2, 0);
  3687. pact = &act;
  3688. } else {
  3689. pact = NULL;
  3690. }
  3691. ret = get_errno(do_sigaction(arg1, pact, &oact));
  3692. if (!is_error(ret) && arg3) {
  3693. if (!lock_user_struct(VERIFY_WRITE, old_act, arg3, 0))
  3694. goto efault;
  3695. old_act->_sa_handler = oact._sa_handler;
  3696. old_act->sa_mask = oact.sa_mask.sig[0];
  3697. old_act->sa_flags = oact.sa_flags;
  3698. old_act->sa_restorer = oact.sa_restorer;
  3699. unlock_user_struct(old_act, arg3, 1);
  3700. }
  3701. #else
  3702. struct target_sigaction act, oact, *pact, *old_act;
  3703. if (arg2) {
  3704. if (!lock_user_struct(VERIFY_READ, old_act, arg2, 1))
  3705. goto efault;
  3706. act._sa_handler = old_act->_sa_handler;
  3707. target_siginitset(&act.sa_mask, old_act->sa_mask.sig[0]);
  3708. act.sa_flags = old_act->sa_flags;
  3709. unlock_user_struct(old_act, arg2, 0);
  3710. pact = &act;
  3711. } else {
  3712. pact = NULL;
  3713. }
  3714. ret = get_errno(do_sigaction(arg1, pact, &oact));
  3715. if (!is_error(ret) && arg3) {
  3716. if (!lock_user_struct(VERIFY_WRITE, old_act, arg3, 0))
  3717. goto efault;
  3718. old_act->_sa_handler = oact._sa_handler;
  3719. old_act->sa_flags = oact.sa_flags;
  3720. old_act->sa_mask.sig[0] = oact.sa_mask.sig[0];
  3721. old_act->sa_mask.sig[1] = 0;
  3722. old_act->sa_mask.sig[2] = 0;
  3723. old_act->sa_mask.sig[3] = 0;
  3724. unlock_user_struct(old_act, arg3, 1);
  3725. }
  3726. #endif
  3727. }
  3728. break;
  3729. #endif
  3730. case TARGET_NR_rt_sigaction:
  3731. {
  3732. struct target_sigaction *act;
  3733. struct target_sigaction *oact;
  3734. if (arg2) {
  3735. if (!lock_user_struct(VERIFY_READ, act, arg2, 1))
  3736. goto efault;
  3737. } else
  3738. act = NULL;
  3739. if (arg3) {
  3740. if (!lock_user_struct(VERIFY_WRITE, oact, arg3, 0)) {
  3741. ret = -TARGET_EFAULT;
  3742. goto rt_sigaction_fail;
  3743. }
  3744. } else
  3745. oact = NULL;
  3746. ret = get_errno(do_sigaction(arg1, act, oact));
  3747. rt_sigaction_fail:
  3748. if (act)
  3749. unlock_user_struct(act, arg2, 0);
  3750. if (oact)
  3751. unlock_user_struct(oact, arg3, 1);
  3752. }
  3753. break;
  3754. #ifdef TARGET_NR_sgetmask /* not on alpha */
  3755. case TARGET_NR_sgetmask:
  3756. {
  3757. sigset_t cur_set;
  3758. abi_ulong target_set;
  3759. sigprocmask(0, NULL, &cur_set);
  3760. host_to_target_old_sigset(&target_set, &cur_set);
  3761. ret = target_set;
  3762. }
  3763. break;
  3764. #endif
  3765. #ifdef TARGET_NR_ssetmask /* not on alpha */
  3766. case TARGET_NR_ssetmask:
  3767. {
  3768. sigset_t set, oset, cur_set;
  3769. abi_ulong target_set = arg1;
  3770. sigprocmask(0, NULL, &cur_set);
  3771. target_to_host_old_sigset(&set, &target_set);
  3772. sigorset(&set, &set, &cur_set);
  3773. sigprocmask(SIG_SETMASK, &set, &oset);
  3774. host_to_target_old_sigset(&target_set, &oset);
  3775. ret = target_set;
  3776. }
  3777. break;
  3778. #endif
  3779. #ifdef TARGET_NR_sigprocmask
  3780. case TARGET_NR_sigprocmask:
  3781. {
  3782. int how = arg1;
  3783. sigset_t set, oldset, *set_ptr;
  3784. if (arg2) {
  3785. switch(how) {
  3786. case TARGET_SIG_BLOCK:
  3787. how = SIG_BLOCK;
  3788. break;
  3789. case TARGET_SIG_UNBLOCK:
  3790. how = SIG_UNBLOCK;
  3791. break;
  3792. case TARGET_SIG_SETMASK:
  3793. how = SIG_SETMASK;
  3794. break;
  3795. default:
  3796. ret = -TARGET_EINVAL;
  3797. goto fail;
  3798. }
  3799. if (!(p = lock_user(VERIFY_READ, arg2, sizeof(target_sigset_t), 1)))
  3800. goto efault;
  3801. target_to_host_old_sigset(&set, p);
  3802. unlock_user(p, arg2, 0);
  3803. set_ptr = &set;
  3804. } else {
  3805. how = 0;
  3806. set_ptr = NULL;
  3807. }
  3808. ret = get_errno(sigprocmask(arg1, set_ptr, &oldset));
  3809. if (!is_error(ret) && arg3) {
  3810. if (!(p = lock_user(VERIFY_WRITE, arg3, sizeof(target_sigset_t), 0)))
  3811. goto efault;
  3812. host_to_target_old_sigset(p, &oldset);
  3813. unlock_user(p, arg3, sizeof(target_sigset_t));
  3814. }
  3815. }
  3816. break;
  3817. #endif
  3818. case TARGET_NR_rt_sigprocmask:
  3819. {
  3820. int how = arg1;
  3821. sigset_t set, oldset, *set_ptr;
  3822. if (arg2) {
  3823. switch(how) {
  3824. case TARGET_SIG_BLOCK:
  3825. how = SIG_BLOCK;
  3826. break;
  3827. case TARGET_SIG_UNBLOCK:
  3828. how = SIG_UNBLOCK;
  3829. break;
  3830. case TARGET_SIG_SETMASK:
  3831. how = SIG_SETMASK;
  3832. break;
  3833. default:
  3834. ret = -TARGET_EINVAL;
  3835. goto fail;
  3836. }
  3837. if (!(p = lock_user(VERIFY_READ, arg2, sizeof(target_sigset_t), 1)))
  3838. goto efault;
  3839. target_to_host_sigset(&set, p);
  3840. unlock_user(p, arg2, 0);
  3841. set_ptr = &set;
  3842. } else {
  3843. how = 0;
  3844. set_ptr = NULL;
  3845. }
  3846. ret = get_errno(sigprocmask(how, set_ptr, &oldset));
  3847. if (!is_error(ret) && arg3) {
  3848. if (!(p = lock_user(VERIFY_WRITE, arg3, sizeof(target_sigset_t), 0)))
  3849. goto efault;
  3850. host_to_target_sigset(p, &oldset);
  3851. unlock_user(p, arg3, sizeof(target_sigset_t));
  3852. }
  3853. }
  3854. break;
  3855. #ifdef TARGET_NR_sigpending
  3856. case TARGET_NR_sigpending:
  3857. {
  3858. sigset_t set;
  3859. ret = get_errno(sigpending(&set));
  3860. if (!is_error(ret)) {
  3861. if (!(p = lock_user(VERIFY_WRITE, arg1, sizeof(target_sigset_t), 0)))
  3862. goto efault;
  3863. host_to_target_old_sigset(p, &set);
  3864. unlock_user(p, arg1, sizeof(target_sigset_t));
  3865. }
  3866. }
  3867. break;
  3868. #endif
  3869. case TARGET_NR_rt_sigpending:
  3870. {
  3871. sigset_t set;
  3872. ret = get_errno(sigpending(&set));
  3873. if (!is_error(ret)) {
  3874. if (!(p = lock_user(VERIFY_WRITE, arg1, sizeof(target_sigset_t), 0)))
  3875. goto efault;
  3876. host_to_target_sigset(p, &set);
  3877. unlock_user(p, arg1, sizeof(target_sigset_t));
  3878. }
  3879. }
  3880. break;
  3881. #ifdef TARGET_NR_sigsuspend
  3882. case TARGET_NR_sigsuspend:
  3883. {
  3884. sigset_t set;
  3885. if (!(p = lock_user(VERIFY_READ, arg1, sizeof(target_sigset_t), 1)))
  3886. goto efault;
  3887. target_to_host_old_sigset(&set, p);
  3888. unlock_user(p, arg1, 0);
  3889. ret = get_errno(sigsuspend(&set));
  3890. }
  3891. break;
  3892. #endif
  3893. case TARGET_NR_rt_sigsuspend:
  3894. {
  3895. sigset_t set;
  3896. if (!(p = lock_user(VERIFY_READ, arg1, sizeof(target_sigset_t), 1)))
  3897. goto efault;
  3898. target_to_host_sigset(&set, p);
  3899. unlock_user(p, arg1, 0);
  3900. ret = get_errno(sigsuspend(&set));
  3901. }
  3902. break;
  3903. case TARGET_NR_rt_sigtimedwait:
  3904. {
  3905. sigset_t set;
  3906. struct timespec uts, *puts;
  3907. siginfo_t uinfo;
  3908. if (!(p = lock_user(VERIFY_READ, arg1, sizeof(target_sigset_t), 1)))
  3909. goto efault;
  3910. target_to_host_sigset(&set, p);
  3911. unlock_user(p, arg1, 0);
  3912. if (arg3) {
  3913. puts = &uts;
  3914. target_to_host_timespec(puts, arg3);
  3915. } else {
  3916. puts = NULL;
  3917. }
  3918. ret = get_errno(sigtimedwait(&set, &uinfo, puts));
  3919. if (!is_error(ret) && arg2) {
  3920. if (!(p = lock_user(VERIFY_WRITE, arg2, sizeof(target_siginfo_t), 0)))
  3921. goto efault;
  3922. host_to_target_siginfo(p, &uinfo);
  3923. unlock_user(p, arg2, sizeof(target_siginfo_t));
  3924. }
  3925. }
  3926. break;
  3927. case TARGET_NR_rt_sigqueueinfo:
  3928. {
  3929. siginfo_t uinfo;
  3930. if (!(p = lock_user(VERIFY_READ, arg3, sizeof(target_sigset_t), 1)))
  3931. goto efault;
  3932. target_to_host_siginfo(&uinfo, p);
  3933. unlock_user(p, arg1, 0);
  3934. ret = get_errno(sys_rt_sigqueueinfo(arg1, arg2, &uinfo));
  3935. }
  3936. break;
  3937. #ifdef TARGET_NR_sigreturn
  3938. case TARGET_NR_sigreturn:
  3939. /* NOTE: ret is eax, so not transcoding must be done */
  3940. ret = do_sigreturn(cpu_env);
  3941. break;
  3942. #endif
  3943. case TARGET_NR_rt_sigreturn:
  3944. /* NOTE: ret is eax, so not transcoding must be done */
  3945. ret = do_rt_sigreturn(cpu_env);
  3946. break;
  3947. case TARGET_NR_sethostname:
  3948. if (!(p = lock_user_string(arg1)))
  3949. goto efault;
  3950. ret = get_errno(sethostname(p, arg2));
  3951. unlock_user(p, arg1, 0);
  3952. break;
  3953. case TARGET_NR_setrlimit:
  3954. {
  3955. /* XXX: convert resource ? */
  3956. int resource = arg1;
  3957. struct target_rlimit *target_rlim;
  3958. struct rlimit rlim;
  3959. if (!lock_user_struct(VERIFY_READ, target_rlim, arg2, 1))
  3960. goto efault;
  3961. rlim.rlim_cur = tswapl(target_rlim->rlim_cur);
  3962. rlim.rlim_max = tswapl(target_rlim->rlim_max);
  3963. unlock_user_struct(target_rlim, arg2, 0);
  3964. ret = get_errno(setrlimit(resource, &rlim));
  3965. }
  3966. break;
  3967. case TARGET_NR_getrlimit:
  3968. {
  3969. /* XXX: convert resource ? */
  3970. int resource = arg1;
  3971. struct target_rlimit *target_rlim;
  3972. struct rlimit rlim;
  3973. ret = get_errno(getrlimit(resource, &rlim));
  3974. if (!is_error(ret)) {
  3975. if (!lock_user_struct(VERIFY_WRITE, target_rlim, arg2, 0))
  3976. goto efault;
  3977. rlim.rlim_cur = tswapl(target_rlim->rlim_cur);
  3978. rlim.rlim_max = tswapl(target_rlim->rlim_max);
  3979. unlock_user_struct(target_rlim, arg2, 1);
  3980. }
  3981. }
  3982. break;
  3983. case TARGET_NR_getrusage:
  3984. {
  3985. struct rusage rusage;
  3986. ret = get_errno(getrusage(arg1, &rusage));
  3987. if (!is_error(ret)) {
  3988. host_to_target_rusage(arg2, &rusage);
  3989. }
  3990. }
  3991. break;
  3992. case TARGET_NR_gettimeofday:
  3993. {
  3994. struct timeval tv;
  3995. ret = get_errno(gettimeofday(&tv, NULL));
  3996. if (!is_error(ret)) {
  3997. if (copy_to_user_timeval(arg1, &tv))
  3998. goto efault;
  3999. }
  4000. }
  4001. break;
  4002. case TARGET_NR_settimeofday:
  4003. {
  4004. struct timeval tv;
  4005. if (copy_from_user_timeval(&tv, arg1))
  4006. goto efault;
  4007. ret = get_errno(settimeofday(&tv, NULL));
  4008. }
  4009. break;
  4010. #ifdef TARGET_NR_select
  4011. case TARGET_NR_select:
  4012. {
  4013. struct target_sel_arg_struct *sel;
  4014. abi_ulong inp, outp, exp, tvp;
  4015. long nsel;
  4016. if (!lock_user_struct(VERIFY_READ, sel, arg1, 1))
  4017. goto efault;
  4018. nsel = tswapl(sel->n);
  4019. inp = tswapl(sel->inp);
  4020. outp = tswapl(sel->outp);
  4021. exp = tswapl(sel->exp);
  4022. tvp = tswapl(sel->tvp);
  4023. unlock_user_struct(sel, arg1, 0);
  4024. ret = do_select(nsel, inp, outp, exp, tvp);
  4025. }
  4026. break;
  4027. #endif
  4028. case TARGET_NR_symlink:
  4029. {
  4030. void *p2;
  4031. p = lock_user_string(arg1);
  4032. p2 = lock_user_string(arg2);
  4033. if (!p || !p2)
  4034. ret = -TARGET_EFAULT;
  4035. else
  4036. ret = get_errno(symlink(p, p2));
  4037. unlock_user(p2, arg2, 0);
  4038. unlock_user(p, arg1, 0);
  4039. }
  4040. break;
  4041. #if defined(TARGET_NR_symlinkat) && defined(__NR_symlinkat)
  4042. case TARGET_NR_symlinkat:
  4043. {
  4044. void *p2;
  4045. p = lock_user_string(arg1);
  4046. p2 = lock_user_string(arg3);
  4047. if (!p || !p2)
  4048. ret = -TARGET_EFAULT;
  4049. else
  4050. ret = get_errno(sys_symlinkat(p, arg2, p2));
  4051. unlock_user(p2, arg3, 0);
  4052. unlock_user(p, arg1, 0);
  4053. }
  4054. break;
  4055. #endif
  4056. #ifdef TARGET_NR_oldlstat
  4057. case TARGET_NR_oldlstat:
  4058. goto unimplemented;
  4059. #endif
  4060. case TARGET_NR_readlink:
  4061. {
  4062. void *p2, *temp;
  4063. p = lock_user_string(arg1);
  4064. p2 = lock_user(VERIFY_WRITE, arg2, arg3, 0);
  4065. if (!p || !p2)
  4066. ret = -TARGET_EFAULT;
  4067. else {
  4068. if (strncmp((const char *)p, "/proc/self/exe", 14) == 0) {
  4069. char real[PATH_MAX];
  4070. temp = realpath(exec_path,real);
  4071. ret = (temp==NULL) ? get_errno(-1) : strlen(real) ;
  4072. snprintf((char *)p2, arg3, "%s", real);
  4073. }
  4074. else
  4075. ret = get_errno(readlink(path(p), p2, arg3));
  4076. }
  4077. unlock_user(p2, arg2, ret);
  4078. unlock_user(p, arg1, 0);
  4079. }
  4080. break;
  4081. #if defined(TARGET_NR_readlinkat) && defined(__NR_readlinkat)
  4082. case TARGET_NR_readlinkat:
  4083. {
  4084. void *p2;
  4085. p = lock_user_string(arg2);
  4086. p2 = lock_user(VERIFY_WRITE, arg3, arg4, 0);
  4087. if (!p || !p2)
  4088. ret = -TARGET_EFAULT;
  4089. else
  4090. ret = get_errno(sys_readlinkat(arg1, path(p), p2, arg4));
  4091. unlock_user(p2, arg3, ret);
  4092. unlock_user(p, arg2, 0);
  4093. }
  4094. break;
  4095. #endif
  4096. #ifdef TARGET_NR_uselib
  4097. case TARGET_NR_uselib:
  4098. goto unimplemented;
  4099. #endif
  4100. #ifdef TARGET_NR_swapon
  4101. case TARGET_NR_swapon:
  4102. if (!(p = lock_user_string(arg1)))
  4103. goto efault;
  4104. ret = get_errno(swapon(p, arg2));
  4105. unlock_user(p, arg1, 0);
  4106. break;
  4107. #endif
  4108. case TARGET_NR_reboot:
  4109. goto unimplemented;
  4110. #ifdef TARGET_NR_readdir
  4111. case TARGET_NR_readdir:
  4112. goto unimplemented;
  4113. #endif
  4114. #ifdef TARGET_NR_mmap
  4115. case TARGET_NR_mmap:
  4116. #if (defined(TARGET_I386) && defined(TARGET_ABI32)) || defined(TARGET_ARM) || defined(TARGET_M68K) || defined(TARGET_CRIS)
  4117. {
  4118. abi_ulong *v;
  4119. abi_ulong v1, v2, v3, v4, v5, v6;
  4120. if (!(v = lock_user(VERIFY_READ, arg1, 6 * sizeof(abi_ulong), 1)))
  4121. goto efault;
  4122. v1 = tswapl(v[0]);
  4123. v2 = tswapl(v[1]);
  4124. v3 = tswapl(v[2]);
  4125. v4 = tswapl(v[3]);
  4126. v5 = tswapl(v[4]);
  4127. v6 = tswapl(v[5]);
  4128. unlock_user(v, arg1, 0);
  4129. ret = get_errno(target_mmap(v1, v2, v3,
  4130. target_to_host_bitmask(v4, mmap_flags_tbl),
  4131. v5, v6));
  4132. }
  4133. #else
  4134. ret = get_errno(target_mmap(arg1, arg2, arg3,
  4135. target_to_host_bitmask(arg4, mmap_flags_tbl),
  4136. arg5,
  4137. arg6));
  4138. #endif
  4139. break;
  4140. #endif
  4141. #ifdef TARGET_NR_mmap2
  4142. case TARGET_NR_mmap2:
  4143. #ifndef MMAP_SHIFT
  4144. #define MMAP_SHIFT 12
  4145. #endif
  4146. ret = get_errno(target_mmap(arg1, arg2, arg3,
  4147. target_to_host_bitmask(arg4, mmap_flags_tbl),
  4148. arg5,
  4149. arg6 << MMAP_SHIFT));
  4150. break;
  4151. #endif
  4152. case TARGET_NR_munmap:
  4153. ret = get_errno(target_munmap(arg1, arg2));
  4154. break;
  4155. case TARGET_NR_mprotect:
  4156. ret = get_errno(target_mprotect(arg1, arg2, arg3));
  4157. break;
  4158. #ifdef TARGET_NR_mremap
  4159. case TARGET_NR_mremap:
  4160. ret = get_errno(target_mremap(arg1, arg2, arg3, arg4, arg5));
  4161. break;
  4162. #endif
  4163. /* ??? msync/mlock/munlock are broken for softmmu. */
  4164. #ifdef TARGET_NR_msync
  4165. case TARGET_NR_msync:
  4166. ret = get_errno(msync(g2h(arg1), arg2, arg3));
  4167. break;
  4168. #endif
  4169. #ifdef TARGET_NR_mlock
  4170. case TARGET_NR_mlock:
  4171. ret = get_errno(mlock(g2h(arg1), arg2));
  4172. break;
  4173. #endif
  4174. #ifdef TARGET_NR_munlock
  4175. case TARGET_NR_munlock:
  4176. ret = get_errno(munlock(g2h(arg1), arg2));
  4177. break;
  4178. #endif
  4179. #ifdef TARGET_NR_mlockall
  4180. case TARGET_NR_mlockall:
  4181. ret = get_errno(mlockall(arg1));
  4182. break;
  4183. #endif
  4184. #ifdef TARGET_NR_munlockall
  4185. case TARGET_NR_munlockall:
  4186. ret = get_errno(munlockall());
  4187. break;
  4188. #endif
  4189. case TARGET_NR_truncate:
  4190. if (!(p = lock_user_string(arg1)))
  4191. goto efault;
  4192. ret = get_errno(truncate(p, arg2));
  4193. unlock_user(p, arg1, 0);
  4194. break;
  4195. case TARGET_NR_ftruncate:
  4196. ret = get_errno(ftruncate(arg1, arg2));
  4197. break;
  4198. case TARGET_NR_fchmod:
  4199. ret = get_errno(fchmod(arg1, arg2));
  4200. break;
  4201. #if defined(TARGET_NR_fchmodat) && defined(__NR_fchmodat)
  4202. case TARGET_NR_fchmodat:
  4203. if (!(p = lock_user_string(arg2)))
  4204. goto efault;
  4205. ret = get_errno(sys_fchmodat(arg1, p, arg3, arg4));
  4206. unlock_user(p, arg2, 0);
  4207. break;
  4208. #endif
  4209. case TARGET_NR_getpriority:
  4210. /* libc does special remapping of the return value of
  4211. * sys_getpriority() so it's just easiest to call
  4212. * sys_getpriority() directly rather than through libc. */
  4213. ret = sys_getpriority(arg1, arg2);
  4214. break;
  4215. case TARGET_NR_setpriority:
  4216. ret = get_errno(setpriority(arg1, arg2, arg3));
  4217. break;
  4218. #ifdef TARGET_NR_profil
  4219. case TARGET_NR_profil:
  4220. goto unimplemented;
  4221. #endif
  4222. case TARGET_NR_statfs:
  4223. if (!(p = lock_user_string(arg1)))
  4224. goto efault;
  4225. ret = get_errno(statfs(path(p), &stfs));
  4226. unlock_user(p, arg1, 0);
  4227. convert_statfs:
  4228. if (!is_error(ret)) {
  4229. struct target_statfs *target_stfs;
  4230. if (!lock_user_struct(VERIFY_WRITE, target_stfs, arg2, 0))
  4231. goto efault;
  4232. __put_user(stfs.f_type, &target_stfs->f_type);
  4233. __put_user(stfs.f_bsize, &target_stfs->f_bsize);
  4234. __put_user(stfs.f_blocks, &target_stfs->f_blocks);
  4235. __put_user(stfs.f_bfree, &target_stfs->f_bfree);
  4236. __put_user(stfs.f_bavail, &target_stfs->f_bavail);
  4237. __put_user(stfs.f_files, &target_stfs->f_files);
  4238. __put_user(stfs.f_ffree, &target_stfs->f_ffree);
  4239. __put_user(stfs.f_fsid.__val[0], &target_stfs->f_fsid.val[0]);
  4240. __put_user(stfs.f_fsid.__val[1], &target_stfs->f_fsid.val[1]);
  4241. __put_user(stfs.f_namelen, &target_stfs->f_namelen);
  4242. unlock_user_struct(target_stfs, arg2, 1);
  4243. }
  4244. break;
  4245. case TARGET_NR_fstatfs:
  4246. ret = get_errno(fstatfs(arg1, &stfs));
  4247. goto convert_statfs;
  4248. #ifdef TARGET_NR_statfs64
  4249. case TARGET_NR_statfs64:
  4250. if (!(p = lock_user_string(arg1)))
  4251. goto efault;
  4252. ret = get_errno(statfs(path(p), &stfs));
  4253. unlock_user(p, arg1, 0);
  4254. convert_statfs64:
  4255. if (!is_error(ret)) {
  4256. struct target_statfs64 *target_stfs;
  4257. if (!lock_user_struct(VERIFY_WRITE, target_stfs, arg3, 0))
  4258. goto efault;
  4259. __put_user(stfs.f_type, &target_stfs->f_type);
  4260. __put_user(stfs.f_bsize, &target_stfs->f_bsize);
  4261. __put_user(stfs.f_blocks, &target_stfs->f_blocks);
  4262. __put_user(stfs.f_bfree, &target_stfs->f_bfree);
  4263. __put_user(stfs.f_bavail, &target_stfs->f_bavail);
  4264. __put_user(stfs.f_files, &target_stfs->f_files);
  4265. __put_user(stfs.f_ffree, &target_stfs->f_ffree);
  4266. __put_user(stfs.f_fsid.__val[0], &target_stfs->f_fsid.val[0]);
  4267. __put_user(stfs.f_fsid.__val[1], &target_stfs->f_fsid.val[1]);
  4268. __put_user(stfs.f_namelen, &target_stfs->f_namelen);
  4269. unlock_user_struct(target_stfs, arg3, 1);
  4270. }
  4271. break;
  4272. case TARGET_NR_fstatfs64:
  4273. ret = get_errno(fstatfs(arg1, &stfs));
  4274. goto convert_statfs64;
  4275. #endif
  4276. #ifdef TARGET_NR_ioperm
  4277. case TARGET_NR_ioperm:
  4278. goto unimplemented;
  4279. #endif
  4280. #ifdef TARGET_NR_socketcall
  4281. case TARGET_NR_socketcall:
  4282. ret = do_socketcall(arg1, arg2);
  4283. break;
  4284. #endif
  4285. #ifdef TARGET_NR_accept
  4286. case TARGET_NR_accept:
  4287. ret = do_accept(arg1, arg2, arg3);
  4288. break;
  4289. #endif
  4290. #ifdef TARGET_NR_bind
  4291. case TARGET_NR_bind:
  4292. ret = do_bind(arg1, arg2, arg3);
  4293. break;
  4294. #endif
  4295. #ifdef TARGET_NR_connect
  4296. case TARGET_NR_connect:
  4297. ret = do_connect(arg1, arg2, arg3);
  4298. break;
  4299. #endif
  4300. #ifdef TARGET_NR_getpeername
  4301. case TARGET_NR_getpeername:
  4302. ret = do_getpeername(arg1, arg2, arg3);
  4303. break;
  4304. #endif
  4305. #ifdef TARGET_NR_getsockname
  4306. case TARGET_NR_getsockname:
  4307. ret = do_getsockname(arg1, arg2, arg3);
  4308. break;
  4309. #endif
  4310. #ifdef TARGET_NR_getsockopt
  4311. case TARGET_NR_getsockopt:
  4312. ret = do_getsockopt(arg1, arg2, arg3, arg4, arg5);
  4313. break;
  4314. #endif
  4315. #ifdef TARGET_NR_listen
  4316. case TARGET_NR_listen:
  4317. ret = get_errno(listen(arg1, arg2));
  4318. break;
  4319. #endif
  4320. #ifdef TARGET_NR_recv
  4321. case TARGET_NR_recv:
  4322. ret = do_recvfrom(arg1, arg2, arg3, arg4, 0, 0);
  4323. break;
  4324. #endif
  4325. #ifdef TARGET_NR_recvfrom
  4326. case TARGET_NR_recvfrom:
  4327. ret = do_recvfrom(arg1, arg2, arg3, arg4, arg5, arg6);
  4328. break;
  4329. #endif
  4330. #ifdef TARGET_NR_recvmsg
  4331. case TARGET_NR_recvmsg:
  4332. ret = do_sendrecvmsg(arg1, arg2, arg3, 0);
  4333. break;
  4334. #endif
  4335. #ifdef TARGET_NR_send
  4336. case TARGET_NR_send:
  4337. ret = do_sendto(arg1, arg2, arg3, arg4, 0, 0);
  4338. break;
  4339. #endif
  4340. #ifdef TARGET_NR_sendmsg
  4341. case TARGET_NR_sendmsg:
  4342. ret = do_sendrecvmsg(arg1, arg2, arg3, 1);
  4343. break;
  4344. #endif
  4345. #ifdef TARGET_NR_sendto
  4346. case TARGET_NR_sendto:
  4347. ret = do_sendto(arg1, arg2, arg3, arg4, arg5, arg6);
  4348. break;
  4349. #endif
  4350. #ifdef TARGET_NR_shutdown
  4351. case TARGET_NR_shutdown:
  4352. ret = get_errno(shutdown(arg1, arg2));
  4353. break;
  4354. #endif
  4355. #ifdef TARGET_NR_socket
  4356. case TARGET_NR_socket:
  4357. ret = do_socket(arg1, arg2, arg3);
  4358. break;
  4359. #endif
  4360. #ifdef TARGET_NR_socketpair
  4361. case TARGET_NR_socketpair:
  4362. ret = do_socketpair(arg1, arg2, arg3, arg4);
  4363. break;
  4364. #endif
  4365. #ifdef TARGET_NR_setsockopt
  4366. case TARGET_NR_setsockopt:
  4367. ret = do_setsockopt(arg1, arg2, arg3, arg4, (socklen_t) arg5);
  4368. break;
  4369. #endif
  4370. case TARGET_NR_syslog:
  4371. if (!(p = lock_user_string(arg2)))
  4372. goto efault;
  4373. ret = get_errno(sys_syslog((int)arg1, p, (int)arg3));
  4374. unlock_user(p, arg2, 0);
  4375. break;
  4376. case TARGET_NR_setitimer:
  4377. {
  4378. struct itimerval value, ovalue, *pvalue;
  4379. if (arg2) {
  4380. pvalue = &value;
  4381. if (copy_from_user_timeval(&pvalue->it_interval, arg2)
  4382. || copy_from_user_timeval(&pvalue->it_value,
  4383. arg2 + sizeof(struct target_timeval)))
  4384. goto efault;
  4385. } else {
  4386. pvalue = NULL;
  4387. }
  4388. ret = get_errno(setitimer(arg1, pvalue, &ovalue));
  4389. if (!is_error(ret) && arg3) {
  4390. if (copy_to_user_timeval(arg3,
  4391. &ovalue.it_interval)
  4392. || copy_to_user_timeval(arg3 + sizeof(struct target_timeval),
  4393. &ovalue.it_value))
  4394. goto efault;
  4395. }
  4396. }
  4397. break;
  4398. case TARGET_NR_getitimer:
  4399. {
  4400. struct itimerval value;
  4401. ret = get_errno(getitimer(arg1, &value));
  4402. if (!is_error(ret) && arg2) {
  4403. if (copy_to_user_timeval(arg2,
  4404. &value.it_interval)
  4405. || copy_to_user_timeval(arg2 + sizeof(struct target_timeval),
  4406. &value.it_value))
  4407. goto efault;
  4408. }
  4409. }
  4410. break;
  4411. case TARGET_NR_stat:
  4412. if (!(p = lock_user_string(arg1)))
  4413. goto efault;
  4414. ret = get_errno(stat(path(p), &st));
  4415. unlock_user(p, arg1, 0);
  4416. goto do_stat;
  4417. case TARGET_NR_lstat:
  4418. if (!(p = lock_user_string(arg1)))
  4419. goto efault;
  4420. ret = get_errno(lstat(path(p), &st));
  4421. unlock_user(p, arg1, 0);
  4422. goto do_stat;
  4423. case TARGET_NR_fstat:
  4424. {
  4425. ret = get_errno(fstat(arg1, &st));
  4426. do_stat:
  4427. if (!is_error(ret)) {
  4428. struct target_stat *target_st;
  4429. if (!lock_user_struct(VERIFY_WRITE, target_st, arg2, 0))
  4430. goto efault;
  4431. __put_user(st.st_dev, &target_st->st_dev);
  4432. __put_user(st.st_ino, &target_st->st_ino);
  4433. __put_user(st.st_mode, &target_st->st_mode);
  4434. __put_user(st.st_uid, &target_st->st_uid);
  4435. __put_user(st.st_gid, &target_st->st_gid);
  4436. __put_user(st.st_nlink, &target_st->st_nlink);
  4437. __put_user(st.st_rdev, &target_st->st_rdev);
  4438. __put_user(st.st_size, &target_st->st_size);
  4439. __put_user(st.st_blksize, &target_st->st_blksize);
  4440. __put_user(st.st_blocks, &target_st->st_blocks);
  4441. __put_user(st.st_atime, &target_st->target_st_atime);
  4442. __put_user(st.st_mtime, &target_st->target_st_mtime);
  4443. __put_user(st.st_ctime, &target_st->target_st_ctime);
  4444. unlock_user_struct(target_st, arg2, 1);
  4445. }
  4446. }
  4447. break;
  4448. #ifdef TARGET_NR_olduname
  4449. case TARGET_NR_olduname:
  4450. goto unimplemented;
  4451. #endif
  4452. #ifdef TARGET_NR_iopl
  4453. case TARGET_NR_iopl:
  4454. goto unimplemented;
  4455. #endif
  4456. case TARGET_NR_vhangup:
  4457. ret = get_errno(vhangup());
  4458. break;
  4459. #ifdef TARGET_NR_idle
  4460. case TARGET_NR_idle:
  4461. goto unimplemented;
  4462. #endif
  4463. #ifdef TARGET_NR_syscall
  4464. case TARGET_NR_syscall:
  4465. ret = do_syscall(cpu_env,arg1 & 0xffff,arg2,arg3,arg4,arg5,arg6,0);
  4466. break;
  4467. #endif
  4468. case TARGET_NR_wait4:
  4469. {
  4470. int status;
  4471. abi_long status_ptr = arg2;
  4472. struct rusage rusage, *rusage_ptr;
  4473. abi_ulong target_rusage = arg4;
  4474. if (target_rusage)
  4475. rusage_ptr = &rusage;
  4476. else
  4477. rusage_ptr = NULL;
  4478. ret = get_errno(wait4(arg1, &status, arg3, rusage_ptr));
  4479. if (!is_error(ret)) {
  4480. if (status_ptr) {
  4481. if (put_user_s32(status, status_ptr))
  4482. goto efault;
  4483. }
  4484. if (target_rusage)
  4485. host_to_target_rusage(target_rusage, &rusage);
  4486. }
  4487. }
  4488. break;
  4489. #ifdef TARGET_NR_swapoff
  4490. case TARGET_NR_swapoff:
  4491. if (!(p = lock_user_string(arg1)))
  4492. goto efault;
  4493. ret = get_errno(swapoff(p));
  4494. unlock_user(p, arg1, 0);
  4495. break;
  4496. #endif
  4497. case TARGET_NR_sysinfo:
  4498. {
  4499. struct target_sysinfo *target_value;
  4500. struct sysinfo value;
  4501. ret = get_errno(sysinfo(&value));
  4502. if (!is_error(ret) && arg1)
  4503. {
  4504. if (!lock_user_struct(VERIFY_WRITE, target_value, arg1, 0))
  4505. goto efault;
  4506. __put_user(value.uptime, &target_value->uptime);
  4507. __put_user(value.loads[0], &target_value->loads[0]);
  4508. __put_user(value.loads[1], &target_value->loads[1]);
  4509. __put_user(value.loads[2], &target_value->loads[2]);
  4510. __put_user(value.totalram, &target_value->totalram);
  4511. __put_user(value.freeram, &target_value->freeram);
  4512. __put_user(value.sharedram, &target_value->sharedram);
  4513. __put_user(value.bufferram, &target_value->bufferram);
  4514. __put_user(value.totalswap, &target_value->totalswap);
  4515. __put_user(value.freeswap, &target_value->freeswap);
  4516. __put_user(value.procs, &target_value->procs);
  4517. __put_user(value.totalhigh, &target_value->totalhigh);
  4518. __put_user(value.freehigh, &target_value->freehigh);
  4519. __put_user(value.mem_unit, &target_value->mem_unit);
  4520. unlock_user_struct(target_value, arg1, 1);
  4521. }
  4522. }
  4523. break;
  4524. #ifdef TARGET_NR_ipc
  4525. case TARGET_NR_ipc:
  4526. ret = do_ipc(arg1, arg2, arg3, arg4, arg5, arg6);
  4527. break;
  4528. #endif
  4529. #ifdef TARGET_NR_msgctl
  4530. case TARGET_NR_msgctl:
  4531. ret = do_msgctl(arg1, arg2, arg3);
  4532. break;
  4533. #endif
  4534. #ifdef TARGET_NR_msgget
  4535. case TARGET_NR_msgget:
  4536. ret = get_errno(msgget(arg1, arg2));
  4537. break;
  4538. #endif
  4539. #ifdef TARGET_NR_msgrcv
  4540. case TARGET_NR_msgrcv:
  4541. ret = do_msgrcv(arg1, arg2, arg3, arg4, arg5);
  4542. break;
  4543. #endif
  4544. #ifdef TARGET_NR_msgsnd
  4545. case TARGET_NR_msgsnd:
  4546. ret = do_msgsnd(arg1, arg2, arg3, arg4);
  4547. break;
  4548. #endif
  4549. case TARGET_NR_fsync:
  4550. ret = get_errno(fsync(arg1));
  4551. break;
  4552. case TARGET_NR_clone:
  4553. #if defined(TARGET_SH4)
  4554. ret = get_errno(do_fork(cpu_env, arg1, arg2, arg3, arg5, arg4));
  4555. #elif defined(TARGET_CRIS)
  4556. ret = get_errno(do_fork(cpu_env, arg2, arg1, arg3, arg4, arg5));
  4557. #else
  4558. ret = get_errno(do_fork(cpu_env, arg1, arg2, arg3, arg4, arg5));
  4559. #endif
  4560. break;
  4561. #ifdef __NR_exit_group
  4562. /* new thread calls */
  4563. case TARGET_NR_exit_group:
  4564. #ifdef HAVE_GPROF
  4565. _mcleanup();
  4566. #endif
  4567. gdb_exit(cpu_env, arg1);
  4568. ret = get_errno(exit_group(arg1));
  4569. break;
  4570. #endif
  4571. case TARGET_NR_setdomainname:
  4572. if (!(p = lock_user_string(arg1)))
  4573. goto efault;
  4574. ret = get_errno(setdomainname(p, arg2));
  4575. unlock_user(p, arg1, 0);
  4576. break;
  4577. case TARGET_NR_uname:
  4578. /* no need to transcode because we use the linux syscall */
  4579. {
  4580. struct new_utsname * buf;
  4581. if (!lock_user_struct(VERIFY_WRITE, buf, arg1, 0))
  4582. goto efault;
  4583. ret = get_errno(sys_uname(buf));
  4584. if (!is_error(ret)) {
  4585. /* Overrite the native machine name with whatever is being
  4586. emulated. */
  4587. strcpy (buf->machine, UNAME_MACHINE);
  4588. /* Allow the user to override the reported release. */
  4589. if (qemu_uname_release && *qemu_uname_release)
  4590. strcpy (buf->release, qemu_uname_release);
  4591. }
  4592. unlock_user_struct(buf, arg1, 1);
  4593. }
  4594. break;
  4595. #ifdef TARGET_I386
  4596. case TARGET_NR_modify_ldt:
  4597. ret = do_modify_ldt(cpu_env, arg1, arg2, arg3);
  4598. break;
  4599. #if !defined(TARGET_X86_64)
  4600. case TARGET_NR_vm86old:
  4601. goto unimplemented;
  4602. case TARGET_NR_vm86:
  4603. ret = do_vm86(cpu_env, arg1, arg2);
  4604. break;
  4605. #endif
  4606. #endif
  4607. case TARGET_NR_adjtimex:
  4608. goto unimplemented;
  4609. #ifdef TARGET_NR_create_module
  4610. case TARGET_NR_create_module:
  4611. #endif
  4612. case TARGET_NR_init_module:
  4613. case TARGET_NR_delete_module:
  4614. #ifdef TARGET_NR_get_kernel_syms
  4615. case TARGET_NR_get_kernel_syms:
  4616. #endif
  4617. goto unimplemented;
  4618. case TARGET_NR_quotactl:
  4619. goto unimplemented;
  4620. case TARGET_NR_getpgid:
  4621. ret = get_errno(getpgid(arg1));
  4622. break;
  4623. case TARGET_NR_fchdir:
  4624. ret = get_errno(fchdir(arg1));
  4625. break;
  4626. #ifdef TARGET_NR_bdflush /* not on x86_64 */
  4627. case TARGET_NR_bdflush:
  4628. goto unimplemented;
  4629. #endif
  4630. #ifdef TARGET_NR_sysfs
  4631. case TARGET_NR_sysfs:
  4632. goto unimplemented;
  4633. #endif
  4634. case TARGET_NR_personality:
  4635. ret = get_errno(personality(arg1));
  4636. break;
  4637. #ifdef TARGET_NR_afs_syscall
  4638. case TARGET_NR_afs_syscall:
  4639. goto unimplemented;
  4640. #endif
  4641. #ifdef TARGET_NR__llseek /* Not on alpha */
  4642. case TARGET_NR__llseek:
  4643. {
  4644. #if defined (__x86_64__)
  4645. ret = get_errno(lseek(arg1, ((uint64_t )arg2 << 32) | arg3, arg5));
  4646. if (put_user_s64(ret, arg4))
  4647. goto efault;
  4648. #else
  4649. int64_t res;
  4650. ret = get_errno(_llseek(arg1, arg2, arg3, &res, arg5));
  4651. if (put_user_s64(res, arg4))
  4652. goto efault;
  4653. #endif
  4654. }
  4655. break;
  4656. #endif
  4657. case TARGET_NR_getdents:
  4658. #if TARGET_ABI_BITS != 32
  4659. goto unimplemented;
  4660. #elif TARGET_ABI_BITS == 32 && HOST_LONG_BITS == 64
  4661. {
  4662. struct target_dirent *target_dirp;
  4663. struct linux_dirent *dirp;
  4664. abi_long count = arg3;
  4665. dirp = malloc(count);
  4666. if (!dirp) {
  4667. ret = -TARGET_ENOMEM;
  4668. goto fail;
  4669. }
  4670. ret = get_errno(sys_getdents(arg1, dirp, count));
  4671. if (!is_error(ret)) {
  4672. struct linux_dirent *de;
  4673. struct target_dirent *tde;
  4674. int len = ret;
  4675. int reclen, treclen;
  4676. int count1, tnamelen;
  4677. count1 = 0;
  4678. de = dirp;
  4679. if (!(target_dirp = lock_user(VERIFY_WRITE, arg2, count, 0)))
  4680. goto efault;
  4681. tde = target_dirp;
  4682. while (len > 0) {
  4683. reclen = de->d_reclen;
  4684. treclen = reclen - (2 * (sizeof(long) - sizeof(abi_long)));
  4685. tde->d_reclen = tswap16(treclen);
  4686. tde->d_ino = tswapl(de->d_ino);
  4687. tde->d_off = tswapl(de->d_off);
  4688. tnamelen = treclen - (2 * sizeof(abi_long) + 2);
  4689. if (tnamelen > 256)
  4690. tnamelen = 256;
  4691. /* XXX: may not be correct */
  4692. pstrcpy(tde->d_name, tnamelen, de->d_name);
  4693. de = (struct linux_dirent *)((char *)de + reclen);
  4694. len -= reclen;
  4695. tde = (struct target_dirent *)((char *)tde + treclen);
  4696. count1 += treclen;
  4697. }
  4698. ret = count1;
  4699. unlock_user(target_dirp, arg2, ret);
  4700. }
  4701. free(dirp);
  4702. }
  4703. #else
  4704. {
  4705. struct linux_dirent *dirp;
  4706. abi_long count = arg3;
  4707. if (!(dirp = lock_user(VERIFY_WRITE, arg2, count, 0)))
  4708. goto efault;
  4709. ret = get_errno(sys_getdents(arg1, dirp, count));
  4710. if (!is_error(ret)) {
  4711. struct linux_dirent *de;
  4712. int len = ret;
  4713. int reclen;
  4714. de = dirp;
  4715. while (len > 0) {
  4716. reclen = de->d_reclen;
  4717. if (reclen > len)
  4718. break;
  4719. de->d_reclen = tswap16(reclen);
  4720. tswapls(&de->d_ino);
  4721. tswapls(&de->d_off);
  4722. de = (struct linux_dirent *)((char *)de + reclen);
  4723. len -= reclen;
  4724. }
  4725. }
  4726. unlock_user(dirp, arg2, ret);
  4727. }
  4728. #endif
  4729. break;
  4730. #if defined(TARGET_NR_getdents64) && defined(__NR_getdents64)
  4731. case TARGET_NR_getdents64:
  4732. {
  4733. struct linux_dirent64 *dirp;
  4734. abi_long count = arg3;
  4735. if (!(dirp = lock_user(VERIFY_WRITE, arg2, count, 0)))
  4736. goto efault;
  4737. ret = get_errno(sys_getdents64(arg1, dirp, count));
  4738. if (!is_error(ret)) {
  4739. struct linux_dirent64 *de;
  4740. int len = ret;
  4741. int reclen;
  4742. de = dirp;
  4743. while (len > 0) {
  4744. reclen = de->d_reclen;
  4745. if (reclen > len)
  4746. break;
  4747. de->d_reclen = tswap16(reclen);
  4748. tswap64s((uint64_t *)&de->d_ino);
  4749. tswap64s((uint64_t *)&de->d_off);
  4750. de = (struct linux_dirent64 *)((char *)de + reclen);
  4751. len -= reclen;
  4752. }
  4753. }
  4754. unlock_user(dirp, arg2, ret);
  4755. }
  4756. break;
  4757. #endif /* TARGET_NR_getdents64 */
  4758. #ifdef TARGET_NR__newselect
  4759. case TARGET_NR__newselect:
  4760. ret = do_select(arg1, arg2, arg3, arg4, arg5);
  4761. break;
  4762. #endif
  4763. #ifdef TARGET_NR_poll
  4764. case TARGET_NR_poll:
  4765. {
  4766. struct target_pollfd *target_pfd;
  4767. unsigned int nfds = arg2;
  4768. int timeout = arg3;
  4769. struct pollfd *pfd;
  4770. unsigned int i;
  4771. target_pfd = lock_user(VERIFY_WRITE, arg1, sizeof(struct target_pollfd) * nfds, 1);
  4772. if (!target_pfd)
  4773. goto efault;
  4774. pfd = alloca(sizeof(struct pollfd) * nfds);
  4775. for(i = 0; i < nfds; i++) {
  4776. pfd[i].fd = tswap32(target_pfd[i].fd);
  4777. pfd[i].events = tswap16(target_pfd[i].events);
  4778. }
  4779. ret = get_errno(poll(pfd, nfds, timeout));
  4780. if (!is_error(ret)) {
  4781. for(i = 0; i < nfds; i++) {
  4782. target_pfd[i].revents = tswap16(pfd[i].revents);
  4783. }
  4784. ret += nfds * (sizeof(struct target_pollfd)
  4785. - sizeof(struct pollfd));
  4786. }
  4787. unlock_user(target_pfd, arg1, ret);
  4788. }
  4789. break;
  4790. #endif
  4791. case TARGET_NR_flock:
  4792. /* NOTE: the flock constant seems to be the same for every
  4793. Linux platform */
  4794. ret = get_errno(flock(arg1, arg2));
  4795. break;
  4796. case TARGET_NR_readv:
  4797. {
  4798. int count = arg3;
  4799. struct iovec *vec;
  4800. vec = alloca(count * sizeof(struct iovec));
  4801. if (lock_iovec(VERIFY_WRITE, vec, arg2, count, 0) < 0)
  4802. goto efault;
  4803. ret = get_errno(readv(arg1, vec, count));
  4804. unlock_iovec(vec, arg2, count, 1);
  4805. }
  4806. break;
  4807. case TARGET_NR_writev:
  4808. {
  4809. int count = arg3;
  4810. struct iovec *vec;
  4811. vec = alloca(count * sizeof(struct iovec));
  4812. if (lock_iovec(VERIFY_READ, vec, arg2, count, 1) < 0)
  4813. goto efault;
  4814. ret = get_errno(writev(arg1, vec, count));
  4815. unlock_iovec(vec, arg2, count, 0);
  4816. }
  4817. break;
  4818. case TARGET_NR_getsid:
  4819. ret = get_errno(getsid(arg1));
  4820. break;
  4821. #if defined(TARGET_NR_fdatasync) /* Not on alpha (osf_datasync ?) */
  4822. case TARGET_NR_fdatasync:
  4823. ret = get_errno(fdatasync(arg1));
  4824. break;
  4825. #endif
  4826. case TARGET_NR__sysctl:
  4827. /* We don't implement this, but ENOTDIR is always a safe
  4828. return value. */
  4829. ret = -TARGET_ENOTDIR;
  4830. break;
  4831. case TARGET_NR_sched_setparam:
  4832. {
  4833. struct sched_param *target_schp;
  4834. struct sched_param schp;
  4835. if (!lock_user_struct(VERIFY_READ, target_schp, arg2, 1))
  4836. goto efault;
  4837. schp.sched_priority = tswap32(target_schp->sched_priority);
  4838. unlock_user_struct(target_schp, arg2, 0);
  4839. ret = get_errno(sched_setparam(arg1, &schp));
  4840. }
  4841. break;
  4842. case TARGET_NR_sched_getparam:
  4843. {
  4844. struct sched_param *target_schp;
  4845. struct sched_param schp;
  4846. ret = get_errno(sched_getparam(arg1, &schp));
  4847. if (!is_error(ret)) {
  4848. if (!lock_user_struct(VERIFY_WRITE, target_schp, arg2, 0))
  4849. goto efault;
  4850. target_schp->sched_priority = tswap32(schp.sched_priority);
  4851. unlock_user_struct(target_schp, arg2, 1);
  4852. }
  4853. }
  4854. break;
  4855. case TARGET_NR_sched_setscheduler:
  4856. {
  4857. struct sched_param *target_schp;
  4858. struct sched_param schp;
  4859. if (!lock_user_struct(VERIFY_READ, target_schp, arg3, 1))
  4860. goto efault;
  4861. schp.sched_priority = tswap32(target_schp->sched_priority);
  4862. unlock_user_struct(target_schp, arg3, 0);
  4863. ret = get_errno(sched_setscheduler(arg1, arg2, &schp));
  4864. }
  4865. break;
  4866. case TARGET_NR_sched_getscheduler:
  4867. ret = get_errno(sched_getscheduler(arg1));
  4868. break;
  4869. case TARGET_NR_sched_yield:
  4870. ret = get_errno(sched_yield());
  4871. break;
  4872. case TARGET_NR_sched_get_priority_max:
  4873. ret = get_errno(sched_get_priority_max(arg1));
  4874. break;
  4875. case TARGET_NR_sched_get_priority_min:
  4876. ret = get_errno(sched_get_priority_min(arg1));
  4877. break;
  4878. case TARGET_NR_sched_rr_get_interval:
  4879. {
  4880. struct timespec ts;
  4881. ret = get_errno(sched_rr_get_interval(arg1, &ts));
  4882. if (!is_error(ret)) {
  4883. host_to_target_timespec(arg2, &ts);
  4884. }
  4885. }
  4886. break;
  4887. case TARGET_NR_nanosleep:
  4888. {
  4889. struct timespec req, rem;
  4890. target_to_host_timespec(&req, arg1);
  4891. ret = get_errno(nanosleep(&req, &rem));
  4892. if (is_error(ret) && arg2) {
  4893. host_to_target_timespec(arg2, &rem);
  4894. }
  4895. }
  4896. break;
  4897. #ifdef TARGET_NR_query_module
  4898. case TARGET_NR_query_module:
  4899. goto unimplemented;
  4900. #endif
  4901. #ifdef TARGET_NR_nfsservctl
  4902. case TARGET_NR_nfsservctl:
  4903. goto unimplemented;
  4904. #endif
  4905. case TARGET_NR_prctl:
  4906. switch (arg1)
  4907. {
  4908. case PR_GET_PDEATHSIG:
  4909. {
  4910. int deathsig;
  4911. ret = get_errno(prctl(arg1, &deathsig, arg3, arg4, arg5));
  4912. if (!is_error(ret) && arg2
  4913. && put_user_ual(deathsig, arg2))
  4914. goto efault;
  4915. }
  4916. break;
  4917. default:
  4918. ret = get_errno(prctl(arg1, arg2, arg3, arg4, arg5));
  4919. break;
  4920. }
  4921. break;
  4922. #ifdef TARGET_NR_arch_prctl
  4923. case TARGET_NR_arch_prctl:
  4924. #if defined(TARGET_I386) && !defined(TARGET_ABI32)
  4925. ret = do_arch_prctl(cpu_env, arg1, arg2);
  4926. break;
  4927. #else
  4928. goto unimplemented;
  4929. #endif
  4930. #endif
  4931. #ifdef TARGET_NR_pread
  4932. case TARGET_NR_pread:
  4933. #ifdef TARGET_ARM
  4934. if (((CPUARMState *)cpu_env)->eabi)
  4935. arg4 = arg5;
  4936. #endif
  4937. if (!(p = lock_user(VERIFY_WRITE, arg2, arg3, 0)))
  4938. goto efault;
  4939. ret = get_errno(pread(arg1, p, arg3, arg4));
  4940. unlock_user(p, arg2, ret);
  4941. break;
  4942. case TARGET_NR_pwrite:
  4943. #ifdef TARGET_ARM
  4944. if (((CPUARMState *)cpu_env)->eabi)
  4945. arg4 = arg5;
  4946. #endif
  4947. if (!(p = lock_user(VERIFY_READ, arg2, arg3, 1)))
  4948. goto efault;
  4949. ret = get_errno(pwrite(arg1, p, arg3, arg4));
  4950. unlock_user(p, arg2, 0);
  4951. break;
  4952. #endif
  4953. #ifdef TARGET_NR_pread64
  4954. case TARGET_NR_pread64:
  4955. if (!(p = lock_user(VERIFY_WRITE, arg2, arg3, 0)))
  4956. goto efault;
  4957. ret = get_errno(pread64(arg1, p, arg3, target_offset64(arg4, arg5)));
  4958. unlock_user(p, arg2, ret);
  4959. break;
  4960. case TARGET_NR_pwrite64:
  4961. if (!(p = lock_user(VERIFY_READ, arg2, arg3, 1)))
  4962. goto efault;
  4963. ret = get_errno(pwrite64(arg1, p, arg3, target_offset64(arg4, arg5)));
  4964. unlock_user(p, arg2, 0);
  4965. break;
  4966. #endif
  4967. case TARGET_NR_getcwd:
  4968. if (!(p = lock_user(VERIFY_WRITE, arg1, arg2, 0)))
  4969. goto efault;
  4970. ret = get_errno(sys_getcwd1(p, arg2));
  4971. unlock_user(p, arg1, ret);
  4972. break;
  4973. case TARGET_NR_capget:
  4974. goto unimplemented;
  4975. case TARGET_NR_capset:
  4976. goto unimplemented;
  4977. case TARGET_NR_sigaltstack:
  4978. #if defined(TARGET_I386) || defined(TARGET_ARM) || defined(TARGET_MIPS) || \
  4979. defined(TARGET_SPARC) || defined(TARGET_PPC) || defined(TARGET_ALPHA)
  4980. ret = do_sigaltstack(arg1, arg2, get_sp_from_cpustate((CPUState *)cpu_env));
  4981. break;
  4982. #else
  4983. goto unimplemented;
  4984. #endif
  4985. case TARGET_NR_sendfile:
  4986. goto unimplemented;
  4987. #ifdef TARGET_NR_getpmsg
  4988. case TARGET_NR_getpmsg:
  4989. goto unimplemented;
  4990. #endif
  4991. #ifdef TARGET_NR_putpmsg
  4992. case TARGET_NR_putpmsg:
  4993. goto unimplemented;
  4994. #endif
  4995. #ifdef TARGET_NR_vfork
  4996. case TARGET_NR_vfork:
  4997. ret = get_errno(do_fork(cpu_env, CLONE_VFORK | CLONE_VM | SIGCHLD,
  4998. 0, 0, 0, 0));
  4999. break;
  5000. #endif
  5001. #ifdef TARGET_NR_ugetrlimit
  5002. case TARGET_NR_ugetrlimit:
  5003. {
  5004. struct rlimit rlim;
  5005. ret = get_errno(getrlimit(arg1, &rlim));
  5006. if (!is_error(ret)) {
  5007. struct target_rlimit *target_rlim;
  5008. if (!lock_user_struct(VERIFY_WRITE, target_rlim, arg2, 0))
  5009. goto efault;
  5010. target_rlim->rlim_cur = tswapl(rlim.rlim_cur);
  5011. target_rlim->rlim_max = tswapl(rlim.rlim_max);
  5012. unlock_user_struct(target_rlim, arg2, 1);
  5013. }
  5014. break;
  5015. }
  5016. #endif
  5017. #ifdef TARGET_NR_truncate64
  5018. case TARGET_NR_truncate64:
  5019. if (!(p = lock_user_string(arg1)))
  5020. goto efault;
  5021. ret = target_truncate64(cpu_env, p, arg2, arg3, arg4);
  5022. unlock_user(p, arg1, 0);
  5023. break;
  5024. #endif
  5025. #ifdef TARGET_NR_ftruncate64
  5026. case TARGET_NR_ftruncate64:
  5027. ret = target_ftruncate64(cpu_env, arg1, arg2, arg3, arg4);
  5028. break;
  5029. #endif
  5030. #ifdef TARGET_NR_stat64
  5031. case TARGET_NR_stat64:
  5032. if (!(p = lock_user_string(arg1)))
  5033. goto efault;
  5034. ret = get_errno(stat(path(p), &st));
  5035. unlock_user(p, arg1, 0);
  5036. if (!is_error(ret))
  5037. ret = host_to_target_stat64(cpu_env, arg2, &st);
  5038. break;
  5039. #endif
  5040. #ifdef TARGET_NR_lstat64
  5041. case TARGET_NR_lstat64:
  5042. if (!(p = lock_user_string(arg1)))
  5043. goto efault;
  5044. ret = get_errno(lstat(path(p), &st));
  5045. unlock_user(p, arg1, 0);
  5046. if (!is_error(ret))
  5047. ret = host_to_target_stat64(cpu_env, arg2, &st);
  5048. break;
  5049. #endif
  5050. #ifdef TARGET_NR_fstat64
  5051. case TARGET_NR_fstat64:
  5052. ret = get_errno(fstat(arg1, &st));
  5053. if (!is_error(ret))
  5054. ret = host_to_target_stat64(cpu_env, arg2, &st);
  5055. break;
  5056. #endif
  5057. #if defined(TARGET_NR_fstatat64) && defined(__NR_fstatat64)
  5058. case TARGET_NR_fstatat64:
  5059. if (!(p = lock_user_string(arg2)))
  5060. goto efault;
  5061. ret = get_errno(sys_fstatat64(arg1, path(p), &st, arg4));
  5062. if (!is_error(ret))
  5063. ret = host_to_target_stat64(cpu_env, arg3, &st);
  5064. break;
  5065. #endif
  5066. #ifdef USE_UID16
  5067. case TARGET_NR_lchown:
  5068. if (!(p = lock_user_string(arg1)))
  5069. goto efault;
  5070. ret = get_errno(lchown(p, low2highuid(arg2), low2highgid(arg3)));
  5071. unlock_user(p, arg1, 0);
  5072. break;
  5073. case TARGET_NR_getuid:
  5074. ret = get_errno(high2lowuid(getuid()));
  5075. break;
  5076. case TARGET_NR_getgid:
  5077. ret = get_errno(high2lowgid(getgid()));
  5078. break;
  5079. case TARGET_NR_geteuid:
  5080. ret = get_errno(high2lowuid(geteuid()));
  5081. break;
  5082. case TARGET_NR_getegid:
  5083. ret = get_errno(high2lowgid(getegid()));
  5084. break;
  5085. case TARGET_NR_setreuid:
  5086. ret = get_errno(setreuid(low2highuid(arg1), low2highuid(arg2)));
  5087. break;
  5088. case TARGET_NR_setregid:
  5089. ret = get_errno(setregid(low2highgid(arg1), low2highgid(arg2)));
  5090. break;
  5091. case TARGET_NR_getgroups:
  5092. {
  5093. int gidsetsize = arg1;
  5094. uint16_t *target_grouplist;
  5095. gid_t *grouplist;
  5096. int i;
  5097. grouplist = alloca(gidsetsize * sizeof(gid_t));
  5098. ret = get_errno(getgroups(gidsetsize, grouplist));
  5099. if (gidsetsize == 0)
  5100. break;
  5101. if (!is_error(ret)) {
  5102. target_grouplist = lock_user(VERIFY_WRITE, arg2, gidsetsize * 2, 0);
  5103. if (!target_grouplist)
  5104. goto efault;
  5105. for(i = 0;i < ret; i++)
  5106. target_grouplist[i] = tswap16(grouplist[i]);
  5107. unlock_user(target_grouplist, arg2, gidsetsize * 2);
  5108. }
  5109. }
  5110. break;
  5111. case TARGET_NR_setgroups:
  5112. {
  5113. int gidsetsize = arg1;
  5114. uint16_t *target_grouplist;
  5115. gid_t *grouplist;
  5116. int i;
  5117. grouplist = alloca(gidsetsize * sizeof(gid_t));
  5118. target_grouplist = lock_user(VERIFY_READ, arg2, gidsetsize * 2, 1);
  5119. if (!target_grouplist) {
  5120. ret = -TARGET_EFAULT;
  5121. goto fail;
  5122. }
  5123. for(i = 0;i < gidsetsize; i++)
  5124. grouplist[i] = tswap16(target_grouplist[i]);
  5125. unlock_user(target_grouplist, arg2, 0);
  5126. ret = get_errno(setgroups(gidsetsize, grouplist));
  5127. }
  5128. break;
  5129. case TARGET_NR_fchown:
  5130. ret = get_errno(fchown(arg1, low2highuid(arg2), low2highgid(arg3)));
  5131. break;
  5132. #if defined(TARGET_NR_fchownat) && defined(__NR_fchownat)
  5133. case TARGET_NR_fchownat:
  5134. if (!(p = lock_user_string(arg2)))
  5135. goto efault;
  5136. ret = get_errno(sys_fchownat(arg1, p, low2highuid(arg3), low2highgid(arg4), arg5));
  5137. unlock_user(p, arg2, 0);
  5138. break;
  5139. #endif
  5140. #ifdef TARGET_NR_setresuid
  5141. case TARGET_NR_setresuid:
  5142. ret = get_errno(setresuid(low2highuid(arg1),
  5143. low2highuid(arg2),
  5144. low2highuid(arg3)));
  5145. break;
  5146. #endif
  5147. #ifdef TARGET_NR_getresuid
  5148. case TARGET_NR_getresuid:
  5149. {
  5150. uid_t ruid, euid, suid;
  5151. ret = get_errno(getresuid(&ruid, &euid, &suid));
  5152. if (!is_error(ret)) {
  5153. if (put_user_u16(high2lowuid(ruid), arg1)
  5154. || put_user_u16(high2lowuid(euid), arg2)
  5155. || put_user_u16(high2lowuid(suid), arg3))
  5156. goto efault;
  5157. }
  5158. }
  5159. break;
  5160. #endif
  5161. #ifdef TARGET_NR_getresgid
  5162. case TARGET_NR_setresgid:
  5163. ret = get_errno(setresgid(low2highgid(arg1),
  5164. low2highgid(arg2),
  5165. low2highgid(arg3)));
  5166. break;
  5167. #endif
  5168. #ifdef TARGET_NR_getresgid
  5169. case TARGET_NR_getresgid:
  5170. {
  5171. gid_t rgid, egid, sgid;
  5172. ret = get_errno(getresgid(&rgid, &egid, &sgid));
  5173. if (!is_error(ret)) {
  5174. if (put_user_u16(high2lowgid(rgid), arg1)
  5175. || put_user_u16(high2lowgid(egid), arg2)
  5176. || put_user_u16(high2lowgid(sgid), arg3))
  5177. goto efault;
  5178. }
  5179. }
  5180. break;
  5181. #endif
  5182. case TARGET_NR_chown:
  5183. if (!(p = lock_user_string(arg1)))
  5184. goto efault;
  5185. ret = get_errno(chown(p, low2highuid(arg2), low2highgid(arg3)));
  5186. unlock_user(p, arg1, 0);
  5187. break;
  5188. case TARGET_NR_setuid:
  5189. ret = get_errno(setuid(low2highuid(arg1)));
  5190. break;
  5191. case TARGET_NR_setgid:
  5192. ret = get_errno(setgid(low2highgid(arg1)));
  5193. break;
  5194. case TARGET_NR_setfsuid:
  5195. ret = get_errno(setfsuid(arg1));
  5196. break;
  5197. case TARGET_NR_setfsgid:
  5198. ret = get_errno(setfsgid(arg1));
  5199. break;
  5200. #endif /* USE_UID16 */
  5201. #ifdef TARGET_NR_lchown32
  5202. case TARGET_NR_lchown32:
  5203. if (!(p = lock_user_string(arg1)))
  5204. goto efault;
  5205. ret = get_errno(lchown(p, arg2, arg3));
  5206. unlock_user(p, arg1, 0);
  5207. break;
  5208. #endif
  5209. #ifdef TARGET_NR_getuid32
  5210. case TARGET_NR_getuid32:
  5211. ret = get_errno(getuid());
  5212. break;
  5213. #endif
  5214. #if defined(TARGET_NR_getxuid) && defined(TARGET_ALPHA)
  5215. /* Alpha specific */
  5216. case TARGET_NR_getxuid:
  5217. {
  5218. uid_t euid;
  5219. euid=geteuid();
  5220. ((CPUAlphaState *)cpu_env)->ir[IR_A4]=euid;
  5221. }
  5222. ret = get_errno(getuid());
  5223. break;
  5224. #endif
  5225. #if defined(TARGET_NR_getxgid) && defined(TARGET_ALPHA)
  5226. /* Alpha specific */
  5227. case TARGET_NR_getxgid:
  5228. {
  5229. uid_t egid;
  5230. egid=getegid();
  5231. ((CPUAlphaState *)cpu_env)->ir[IR_A4]=egid;
  5232. }
  5233. ret = get_errno(getgid());
  5234. break;
  5235. #endif
  5236. #ifdef TARGET_NR_getgid32
  5237. case TARGET_NR_getgid32:
  5238. ret = get_errno(getgid());
  5239. break;
  5240. #endif
  5241. #ifdef TARGET_NR_geteuid32
  5242. case TARGET_NR_geteuid32:
  5243. ret = get_errno(geteuid());
  5244. break;
  5245. #endif
  5246. #ifdef TARGET_NR_getegid32
  5247. case TARGET_NR_getegid32:
  5248. ret = get_errno(getegid());
  5249. break;
  5250. #endif
  5251. #ifdef TARGET_NR_setreuid32
  5252. case TARGET_NR_setreuid32:
  5253. ret = get_errno(setreuid(arg1, arg2));
  5254. break;
  5255. #endif
  5256. #ifdef TARGET_NR_setregid32
  5257. case TARGET_NR_setregid32:
  5258. ret = get_errno(setregid(arg1, arg2));
  5259. break;
  5260. #endif
  5261. #ifdef TARGET_NR_getgroups32
  5262. case TARGET_NR_getgroups32:
  5263. {
  5264. int gidsetsize = arg1;
  5265. uint32_t *target_grouplist;
  5266. gid_t *grouplist;
  5267. int i;
  5268. grouplist = alloca(gidsetsize * sizeof(gid_t));
  5269. ret = get_errno(getgroups(gidsetsize, grouplist));
  5270. if (gidsetsize == 0)
  5271. break;
  5272. if (!is_error(ret)) {
  5273. target_grouplist = lock_user(VERIFY_WRITE, arg2, gidsetsize * 4, 0);
  5274. if (!target_grouplist) {
  5275. ret = -TARGET_EFAULT;
  5276. goto fail;
  5277. }
  5278. for(i = 0;i < ret; i++)
  5279. target_grouplist[i] = tswap32(grouplist[i]);
  5280. unlock_user(target_grouplist, arg2, gidsetsize * 4);
  5281. }
  5282. }
  5283. break;
  5284. #endif
  5285. #ifdef TARGET_NR_setgroups32
  5286. case TARGET_NR_setgroups32:
  5287. {
  5288. int gidsetsize = arg1;
  5289. uint32_t *target_grouplist;
  5290. gid_t *grouplist;
  5291. int i;
  5292. grouplist = alloca(gidsetsize * sizeof(gid_t));
  5293. target_grouplist = lock_user(VERIFY_READ, arg2, gidsetsize * 4, 1);
  5294. if (!target_grouplist) {
  5295. ret = -TARGET_EFAULT;
  5296. goto fail;
  5297. }
  5298. for(i = 0;i < gidsetsize; i++)
  5299. grouplist[i] = tswap32(target_grouplist[i]);
  5300. unlock_user(target_grouplist, arg2, 0);
  5301. ret = get_errno(setgroups(gidsetsize, grouplist));
  5302. }
  5303. break;
  5304. #endif
  5305. #ifdef TARGET_NR_fchown32
  5306. case TARGET_NR_fchown32:
  5307. ret = get_errno(fchown(arg1, arg2, arg3));
  5308. break;
  5309. #endif
  5310. #ifdef TARGET_NR_setresuid32
  5311. case TARGET_NR_setresuid32:
  5312. ret = get_errno(setresuid(arg1, arg2, arg3));
  5313. break;
  5314. #endif
  5315. #ifdef TARGET_NR_getresuid32
  5316. case TARGET_NR_getresuid32:
  5317. {
  5318. uid_t ruid, euid, suid;
  5319. ret = get_errno(getresuid(&ruid, &euid, &suid));
  5320. if (!is_error(ret)) {
  5321. if (put_user_u32(ruid, arg1)
  5322. || put_user_u32(euid, arg2)
  5323. || put_user_u32(suid, arg3))
  5324. goto efault;
  5325. }
  5326. }
  5327. break;
  5328. #endif
  5329. #ifdef TARGET_NR_setresgid32
  5330. case TARGET_NR_setresgid32:
  5331. ret = get_errno(setresgid(arg1, arg2, arg3));
  5332. break;
  5333. #endif
  5334. #ifdef TARGET_NR_getresgid32
  5335. case TARGET_NR_getresgid32:
  5336. {
  5337. gid_t rgid, egid, sgid;
  5338. ret = get_errno(getresgid(&rgid, &egid, &sgid));
  5339. if (!is_error(ret)) {
  5340. if (put_user_u32(rgid, arg1)
  5341. || put_user_u32(egid, arg2)
  5342. || put_user_u32(sgid, arg3))
  5343. goto efault;
  5344. }
  5345. }
  5346. break;
  5347. #endif
  5348. #ifdef TARGET_NR_chown32
  5349. case TARGET_NR_chown32:
  5350. if (!(p = lock_user_string(arg1)))
  5351. goto efault;
  5352. ret = get_errno(chown(p, arg2, arg3));
  5353. unlock_user(p, arg1, 0);
  5354. break;
  5355. #endif
  5356. #ifdef TARGET_NR_setuid32
  5357. case TARGET_NR_setuid32:
  5358. ret = get_errno(setuid(arg1));
  5359. break;
  5360. #endif
  5361. #ifdef TARGET_NR_setgid32
  5362. case TARGET_NR_setgid32:
  5363. ret = get_errno(setgid(arg1));
  5364. break;
  5365. #endif
  5366. #ifdef TARGET_NR_setfsuid32
  5367. case TARGET_NR_setfsuid32:
  5368. ret = get_errno(setfsuid(arg1));
  5369. break;
  5370. #endif
  5371. #ifdef TARGET_NR_setfsgid32
  5372. case TARGET_NR_setfsgid32:
  5373. ret = get_errno(setfsgid(arg1));
  5374. break;
  5375. #endif
  5376. case TARGET_NR_pivot_root:
  5377. goto unimplemented;
  5378. #ifdef TARGET_NR_mincore
  5379. case TARGET_NR_mincore:
  5380. {
  5381. void *a;
  5382. ret = -TARGET_EFAULT;
  5383. if (!(a = lock_user(VERIFY_READ, arg1,arg2, 0)))
  5384. goto efault;
  5385. if (!(p = lock_user_string(arg3)))
  5386. goto mincore_fail;
  5387. ret = get_errno(mincore(a, arg2, p));
  5388. unlock_user(p, arg3, ret);
  5389. mincore_fail:
  5390. unlock_user(a, arg1, 0);
  5391. }
  5392. break;
  5393. #endif
  5394. #ifdef TARGET_NR_arm_fadvise64_64
  5395. case TARGET_NR_arm_fadvise64_64:
  5396. {
  5397. /*
  5398. * arm_fadvise64_64 looks like fadvise64_64 but
  5399. * with different argument order
  5400. */
  5401. abi_long temp;
  5402. temp = arg3;
  5403. arg3 = arg4;
  5404. arg4 = temp;
  5405. }
  5406. #endif
  5407. #if defined(TARGET_NR_fadvise64_64) || defined(TARGET_NR_arm_fadvise64_64)
  5408. #ifdef TARGET_NR_fadvise64_64
  5409. case TARGET_NR_fadvise64_64:
  5410. #endif
  5411. /* This is a hint, so ignoring and returning success is ok. */
  5412. ret = get_errno(0);
  5413. break;
  5414. #endif
  5415. #ifdef TARGET_NR_madvise
  5416. case TARGET_NR_madvise:
  5417. /* A straight passthrough may not be safe because qemu sometimes
  5418. turns private flie-backed mappings into anonymous mappings.
  5419. This will break MADV_DONTNEED.
  5420. This is a hint, so ignoring and returning success is ok. */
  5421. ret = get_errno(0);
  5422. break;
  5423. #endif
  5424. #if TARGET_ABI_BITS == 32
  5425. case TARGET_NR_fcntl64:
  5426. {
  5427. int cmd;
  5428. struct flock64 fl;
  5429. struct target_flock64 *target_fl;
  5430. #ifdef TARGET_ARM
  5431. struct target_eabi_flock64 *target_efl;
  5432. #endif
  5433. switch(arg2){
  5434. case TARGET_F_GETLK64:
  5435. cmd = F_GETLK64;
  5436. break;
  5437. case TARGET_F_SETLK64:
  5438. cmd = F_SETLK64;
  5439. break;
  5440. case TARGET_F_SETLKW64:
  5441. cmd = F_SETLK64;
  5442. break;
  5443. default:
  5444. cmd = arg2;
  5445. break;
  5446. }
  5447. switch(arg2) {
  5448. case TARGET_F_GETLK64:
  5449. #ifdef TARGET_ARM
  5450. if (((CPUARMState *)cpu_env)->eabi) {
  5451. if (!lock_user_struct(VERIFY_READ, target_efl, arg3, 1))
  5452. goto efault;
  5453. fl.l_type = tswap16(target_efl->l_type);
  5454. fl.l_whence = tswap16(target_efl->l_whence);
  5455. fl.l_start = tswap64(target_efl->l_start);
  5456. fl.l_len = tswap64(target_efl->l_len);
  5457. fl.l_pid = tswapl(target_efl->l_pid);
  5458. unlock_user_struct(target_efl, arg3, 0);
  5459. } else
  5460. #endif
  5461. {
  5462. if (!lock_user_struct(VERIFY_READ, target_fl, arg3, 1))
  5463. goto efault;
  5464. fl.l_type = tswap16(target_fl->l_type);
  5465. fl.l_whence = tswap16(target_fl->l_whence);
  5466. fl.l_start = tswap64(target_fl->l_start);
  5467. fl.l_len = tswap64(target_fl->l_len);
  5468. fl.l_pid = tswapl(target_fl->l_pid);
  5469. unlock_user_struct(target_fl, arg3, 0);
  5470. }
  5471. ret = get_errno(fcntl(arg1, cmd, &fl));
  5472. if (ret == 0) {
  5473. #ifdef TARGET_ARM
  5474. if (((CPUARMState *)cpu_env)->eabi) {
  5475. if (!lock_user_struct(VERIFY_WRITE, target_efl, arg3, 0))
  5476. goto efault;
  5477. target_efl->l_type = tswap16(fl.l_type);
  5478. target_efl->l_whence = tswap16(fl.l_whence);
  5479. target_efl->l_start = tswap64(fl.l_start);
  5480. target_efl->l_len = tswap64(fl.l_len);
  5481. target_efl->l_pid = tswapl(fl.l_pid);
  5482. unlock_user_struct(target_efl, arg3, 1);
  5483. } else
  5484. #endif
  5485. {
  5486. if (!lock_user_struct(VERIFY_WRITE, target_fl, arg3, 0))
  5487. goto efault;
  5488. target_fl->l_type = tswap16(fl.l_type);
  5489. target_fl->l_whence = tswap16(fl.l_whence);
  5490. target_fl->l_start = tswap64(fl.l_start);
  5491. target_fl->l_len = tswap64(fl.l_len);
  5492. target_fl->l_pid = tswapl(fl.l_pid);
  5493. unlock_user_struct(target_fl, arg3, 1);
  5494. }
  5495. }
  5496. break;
  5497. case TARGET_F_SETLK64:
  5498. case TARGET_F_SETLKW64:
  5499. #ifdef TARGET_ARM
  5500. if (((CPUARMState *)cpu_env)->eabi) {
  5501. if (!lock_user_struct(VERIFY_READ, target_efl, arg3, 1))
  5502. goto efault;
  5503. fl.l_type = tswap16(target_efl->l_type);
  5504. fl.l_whence = tswap16(target_efl->l_whence);
  5505. fl.l_start = tswap64(target_efl->l_start);
  5506. fl.l_len = tswap64(target_efl->l_len);
  5507. fl.l_pid = tswapl(target_efl->l_pid);
  5508. unlock_user_struct(target_efl, arg3, 0);
  5509. } else
  5510. #endif
  5511. {
  5512. if (!lock_user_struct(VERIFY_READ, target_fl, arg3, 1))
  5513. goto efault;
  5514. fl.l_type = tswap16(target_fl->l_type);
  5515. fl.l_whence = tswap16(target_fl->l_whence);
  5516. fl.l_start = tswap64(target_fl->l_start);
  5517. fl.l_len = tswap64(target_fl->l_len);
  5518. fl.l_pid = tswapl(target_fl->l_pid);
  5519. unlock_user_struct(target_fl, arg3, 0);
  5520. }
  5521. ret = get_errno(fcntl(arg1, cmd, &fl));
  5522. break;
  5523. default:
  5524. ret = do_fcntl(arg1, cmd, arg3);
  5525. break;
  5526. }
  5527. break;
  5528. }
  5529. #endif
  5530. #ifdef TARGET_NR_cacheflush
  5531. case TARGET_NR_cacheflush:
  5532. /* self-modifying code is handled automatically, so nothing needed */
  5533. ret = 0;
  5534. break;
  5535. #endif
  5536. #ifdef TARGET_NR_security
  5537. case TARGET_NR_security:
  5538. goto unimplemented;
  5539. #endif
  5540. #ifdef TARGET_NR_getpagesize
  5541. case TARGET_NR_getpagesize:
  5542. ret = TARGET_PAGE_SIZE;
  5543. break;
  5544. #endif
  5545. case TARGET_NR_gettid:
  5546. ret = get_errno(gettid());
  5547. break;
  5548. #ifdef TARGET_NR_readahead
  5549. case TARGET_NR_readahead:
  5550. #if TARGET_ABI_BITS == 32
  5551. #ifdef TARGET_ARM
  5552. if (((CPUARMState *)cpu_env)->eabi)
  5553. {
  5554. arg2 = arg3;
  5555. arg3 = arg4;
  5556. arg4 = arg5;
  5557. }
  5558. #endif
  5559. ret = get_errno(readahead(arg1, ((off64_t)arg3 << 32) | arg2, arg4));
  5560. #else
  5561. ret = get_errno(readahead(arg1, arg2, arg3));
  5562. #endif
  5563. break;
  5564. #endif
  5565. #ifdef TARGET_NR_setxattr
  5566. case TARGET_NR_setxattr:
  5567. case TARGET_NR_lsetxattr:
  5568. case TARGET_NR_fsetxattr:
  5569. case TARGET_NR_getxattr:
  5570. case TARGET_NR_lgetxattr:
  5571. case TARGET_NR_fgetxattr:
  5572. case TARGET_NR_listxattr:
  5573. case TARGET_NR_llistxattr:
  5574. case TARGET_NR_flistxattr:
  5575. case TARGET_NR_removexattr:
  5576. case TARGET_NR_lremovexattr:
  5577. case TARGET_NR_fremovexattr:
  5578. goto unimplemented_nowarn;
  5579. #endif
  5580. #ifdef TARGET_NR_set_thread_area
  5581. case TARGET_NR_set_thread_area:
  5582. #if defined(TARGET_MIPS)
  5583. ((CPUMIPSState *) cpu_env)->tls_value = arg1;
  5584. ret = 0;
  5585. break;
  5586. #elif defined(TARGET_CRIS)
  5587. if (arg1 & 0xff)
  5588. ret = -TARGET_EINVAL;
  5589. else {
  5590. ((CPUCRISState *) cpu_env)->pregs[PR_PID] = arg1;
  5591. ret = 0;
  5592. }
  5593. break;
  5594. #elif defined(TARGET_I386) && defined(TARGET_ABI32)
  5595. ret = do_set_thread_area(cpu_env, arg1);
  5596. break;
  5597. #else
  5598. goto unimplemented_nowarn;
  5599. #endif
  5600. #endif
  5601. #ifdef TARGET_NR_get_thread_area
  5602. case TARGET_NR_get_thread_area:
  5603. #if defined(TARGET_I386) && defined(TARGET_ABI32)
  5604. ret = do_get_thread_area(cpu_env, arg1);
  5605. #else
  5606. goto unimplemented_nowarn;
  5607. #endif
  5608. #endif
  5609. #ifdef TARGET_NR_getdomainname
  5610. case TARGET_NR_getdomainname:
  5611. goto unimplemented_nowarn;
  5612. #endif
  5613. #ifdef TARGET_NR_clock_gettime
  5614. case TARGET_NR_clock_gettime:
  5615. {
  5616. struct timespec ts;
  5617. ret = get_errno(clock_gettime(arg1, &ts));
  5618. if (!is_error(ret)) {
  5619. host_to_target_timespec(arg2, &ts);
  5620. }
  5621. break;
  5622. }
  5623. #endif
  5624. #ifdef TARGET_NR_clock_getres
  5625. case TARGET_NR_clock_getres:
  5626. {
  5627. struct timespec ts;
  5628. ret = get_errno(clock_getres(arg1, &ts));
  5629. if (!is_error(ret)) {
  5630. host_to_target_timespec(arg2, &ts);
  5631. }
  5632. break;
  5633. }
  5634. #endif
  5635. #ifdef TARGET_NR_clock_nanosleep
  5636. case TARGET_NR_clock_nanosleep:
  5637. {
  5638. struct timespec ts;
  5639. target_to_host_timespec(&ts, arg3);
  5640. ret = get_errno(clock_nanosleep(arg1, arg2, &ts, arg4 ? &ts : NULL));
  5641. if (arg4)
  5642. host_to_target_timespec(arg4, &ts);
  5643. break;
  5644. }
  5645. #endif
  5646. #if defined(TARGET_NR_set_tid_address) && defined(__NR_set_tid_address)
  5647. case TARGET_NR_set_tid_address:
  5648. ret = get_errno(set_tid_address((int *)g2h(arg1)));
  5649. break;
  5650. #endif
  5651. #if defined(TARGET_NR_tkill) && defined(__NR_tkill)
  5652. case TARGET_NR_tkill:
  5653. ret = get_errno(sys_tkill((int)arg1, target_to_host_signal(arg2)));
  5654. break;
  5655. #endif
  5656. #if defined(TARGET_NR_tgkill) && defined(__NR_tgkill)
  5657. case TARGET_NR_tgkill:
  5658. ret = get_errno(sys_tgkill((int)arg1, (int)arg2,
  5659. target_to_host_signal(arg3)));
  5660. break;
  5661. #endif
  5662. #ifdef TARGET_NR_set_robust_list
  5663. case TARGET_NR_set_robust_list:
  5664. goto unimplemented_nowarn;
  5665. #endif
  5666. #if defined(TARGET_NR_utimensat) && defined(__NR_utimensat)
  5667. case TARGET_NR_utimensat:
  5668. {
  5669. struct timespec ts[2];
  5670. target_to_host_timespec(ts, arg3);
  5671. target_to_host_timespec(ts+1, arg3+sizeof(struct target_timespec));
  5672. if (!arg2)
  5673. ret = get_errno(sys_utimensat(arg1, NULL, ts, arg4));
  5674. else {
  5675. if (!(p = lock_user_string(arg2))) {
  5676. ret = -TARGET_EFAULT;
  5677. goto fail;
  5678. }
  5679. ret = get_errno(sys_utimensat(arg1, path(p), ts, arg4));
  5680. unlock_user(p, arg2, 0);
  5681. }
  5682. }
  5683. break;
  5684. #endif
  5685. #if defined(USE_NPTL)
  5686. case TARGET_NR_futex:
  5687. ret = do_futex(arg1, arg2, arg3, arg4, arg5, arg6);
  5688. break;
  5689. #endif
  5690. #ifdef TARGET_NR_inotify_init
  5691. case TARGET_NR_inotify_init:
  5692. ret = get_errno(sys_inotify_init());
  5693. break;
  5694. #endif
  5695. #ifdef TARGET_NR_inotify_add_watch
  5696. case TARGET_NR_inotify_add_watch:
  5697. p = lock_user_string(arg2);
  5698. ret = get_errno(sys_inotify_add_watch(arg1, path(p), arg3));
  5699. unlock_user(p, arg2, 0);
  5700. break;
  5701. #endif
  5702. #ifdef TARGET_NR_inotify_rm_watch
  5703. case TARGET_NR_inotify_rm_watch:
  5704. ret = get_errno(sys_inotify_rm_watch(arg1, arg2));
  5705. break;
  5706. #endif
  5707. default:
  5708. unimplemented:
  5709. gemu_log("qemu: Unsupported syscall: %d\n", num);
  5710. #if defined(TARGET_NR_setxattr) || defined(TARGET_NR_get_thread_area) || defined(TARGET_NR_getdomainname) || defined(TARGET_NR_set_robust_list)
  5711. unimplemented_nowarn:
  5712. #endif
  5713. ret = -TARGET_ENOSYS;
  5714. break;
  5715. }
  5716. fail:
  5717. #ifdef DEBUG
  5718. gemu_log(" = %ld\n", ret);
  5719. #endif
  5720. if(do_strace)
  5721. print_syscall_ret(num, ret);
  5722. return ret;
  5723. efault:
  5724. ret = -TARGET_EFAULT;
  5725. goto fail;
  5726. }