emul_unix.c 72 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341234223432344234523462347234823492350235123522353235423552356235723582359236023612362236323642365236623672368236923702371237223732374237523762377237823792380238123822383238423852386238723882389239023912392239323942395239623972398239924002401240224032404240524062407240824092410241124122413241424152416241724182419242024212422242324242425242624272428242924302431243224332434243524362437243824392440244124422443244424452446244724482449245024512452245324542455245624572458245924602461246224632464246524662467246824692470247124722473247424752476247724782479248024812482248324842485248624872488248924902491249224932494249524962497249824992500250125022503250425052506250725082509251025112512251325142515251625172518251925202521252225232524252525262527252825292530253125322533253425352536253725382539254025412542254325442545254625472548254925502551255225532554255525562557255825592560256125622563256425652566256725682569257025712572257325742575257625772578257925802581258225832584258525862587258825892590259125922593259425952596259725982599260026012602260326042605260626072608260926102611261226132614261526162617261826192620262126222623262426252626262726282629263026312632263326342635263626372638263926402641264226432644264526462647264826492650265126522653265426552656265726582659266026612662266326642665266626672668266926702671267226732674267526762677267826792680268126822683268426852686268726882689269026912692269326942695269626972698269927002701270227032704270527062707270827092710271127122713271427152716271727182719272027212722272327242725272627272728272927302731273227332734273527362737273827392740274127422743274427452746274727482749275027512752275327542755275627572758275927602761276227632764276527662767276827692770277127722773277427752776277727782779278027812782278327842785278627872788278927902791279227932794279527962797279827992800280128022803280428052806280728082809281028112812281328142815281628172818281928202821282228232824282528262827282828292830283128322833283428352836283728382839284028412842284328442845284628472848284928502851285228532854285528562857285828592860286128622863286428652866286728682869287028712872
  1. /* This file is part of the program psim.
  2. Copyright (C) 1996-1998, Andrew Cagney <cagney@highland.com.au>
  3. This program is free software; you can redistribute it and/or modify
  4. it under the terms of the GNU General Public License as published by
  5. the Free Software Foundation; either version 3 of the License, or
  6. (at your option) any later version.
  7. This program is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  10. GNU General Public License for more details.
  11. You should have received a copy of the GNU General Public License
  12. along with this program; if not, see <http://www.gnu.org/licenses/>.
  13. */
  14. #ifndef _EMUL_UNIX_C_
  15. #define _EMUL_UNIX_C_
  16. /* Note: this module is called via a table. There is no benefit in
  17. making it inline */
  18. #include "defs.h"
  19. #include <string.h>
  20. #ifdef HAVE_SYS_TYPES_H
  21. #include <sys/types.h>
  22. #endif
  23. #ifdef HAVE_SYS_TYPES_H
  24. #include <sys/stat.h>
  25. #else
  26. #undef HAVE_STAT
  27. #undef HAVE_LSTAT
  28. #undef HAVE_FSTAT
  29. #endif
  30. #include <stdio.h>
  31. #include <signal.h>
  32. #include <errno.h>
  33. #ifdef HAVE_FCNTL_H
  34. #include <fcntl.h>
  35. #endif
  36. #ifdef HAVE_SYS_PARAM_H
  37. #include <sys/param.h>
  38. #endif
  39. #include <sys/time.h>
  40. #ifndef HAVE_TERMIOS_STRUCTURE
  41. #undef HAVE_SYS_TERMIOS_H
  42. #undef HAVE_TCGETATTR
  43. #else
  44. #ifndef HAVE_SYS_TERMIOS_H
  45. #undef HAVE_TERMIOS_STRUCTURE
  46. #endif
  47. #endif
  48. #ifdef HAVE_TERMIOS_STRUCTURE
  49. #include <sys/termios.h>
  50. /* If we have TERMIOS, use that for the termio structure, since some systems
  51. don't like including both sys/termios.h and sys/termio.h at the same
  52. time. */
  53. #undef HAVE_TERMIO_STRUCTURE
  54. #undef TCGETA
  55. #undef termio
  56. #define termio termios
  57. #endif
  58. #ifndef HAVE_TERMIO_STRUCTURE
  59. #undef HAVE_SYS_TERMIO_H
  60. #else
  61. #ifndef HAVE_SYS_TERMIO_H
  62. #undef HAVE_TERMIO_STRUCTURE
  63. #endif
  64. #endif
  65. #ifdef HAVE_TERMIO_STRUCTURE
  66. #include <sys/termio.h>
  67. #endif
  68. #ifdef HAVE_GETRUSAGE
  69. #ifndef HAVE_SYS_RESOURCE_H
  70. #undef HAVE_GETRUSAGE
  71. #endif
  72. #endif
  73. #ifdef HAVE_GETRUSAGE
  74. #include <sys/resource.h>
  75. int getrusage();
  76. #endif
  77. #if HAVE_DIRENT_H
  78. # include <dirent.h>
  79. # define NAMLEN(dirent) strlen((dirent)->d_name)
  80. #else
  81. # define dirent direct
  82. # define NAMLEN(dirent) (dirent)->d_namlen
  83. # if HAVE_SYS_NDIR_H
  84. # include <sys/ndir.h>
  85. # endif
  86. # if HAVE_SYS_DIR_H
  87. # include <sys/dir.h>
  88. # endif
  89. # if HAVE_NDIR_H
  90. # include <ndir.h>
  91. # endif
  92. #endif
  93. #ifdef HAVE_UNISTD_H
  94. #undef MAXPATHLEN /* sys/param.h might define this also */
  95. #include <unistd.h>
  96. #endif
  97. #include <stdlib.h>
  98. #include <time.h>
  99. #include "emul_generic.h"
  100. #include "emul_unix.h"
  101. #ifndef STATIC_INLINE_EMUL_UNIX
  102. #define STATIC_INLINE_EMUL_UNIX STATIC_INLINE
  103. #endif
  104. #ifndef PATH_MAX
  105. #define PATH_MAX 1024
  106. #endif
  107. #ifndef EINVAL
  108. #define EINVAL -1
  109. #endif
  110. /* UNIX's idea of what is needed to implement emulations */
  111. struct _os_emul_data {
  112. device *vm;
  113. emul_syscall *syscalls;
  114. };
  115. /* Emulation of simple UNIX system calls that are common on all systems. */
  116. /* Structures that are common agmonst the UNIX varients */
  117. struct unix_timeval {
  118. int32_t tv_sec; /* seconds */
  119. int32_t tv_usec; /* microseconds */
  120. };
  121. struct unix_timezone {
  122. int32_t tz_minuteswest; /* minutes west of Greenwich */
  123. int32_t tz_dsttime; /* type of dst correction */
  124. };
  125. #define UNIX_RUSAGE_SELF 0
  126. #define UNIX_RUSAGE_CHILDREN (-1)
  127. #define UNIX_RUSAGE_BOTH (-2) /* sys_wait4() uses this */
  128. struct unix_rusage {
  129. struct unix_timeval ru_utime; /* user time used */
  130. struct unix_timeval ru_stime; /* system time used */
  131. int32_t ru_maxrss; /* maximum resident set size */
  132. int32_t ru_ixrss; /* integral shared memory size */
  133. int32_t ru_idrss; /* integral unshared data size */
  134. int32_t ru_isrss; /* integral unshared stack size */
  135. int32_t ru_minflt; /* any page faults not requiring I/O */
  136. int32_t ru_majflt; /* any page faults requiring I/O */
  137. int32_t ru_nswap; /* swaps */
  138. int32_t ru_inblock; /* block input operations */
  139. int32_t ru_oublock; /* block output operations */
  140. int32_t ru_msgsnd; /* messages sent */
  141. int32_t ru_msgrcv; /* messages received */
  142. int32_t ru_nsignals; /* signals received */
  143. int32_t ru_nvcsw; /* voluntary context switches */
  144. int32_t ru_nivcsw; /* involuntary " */
  145. };
  146. /* File descriptors 0, 1, and 2 should not be closed. fd_closed[]
  147. tracks whether these descriptors have been closed in do_close()
  148. below. */
  149. static int fd_closed[3];
  150. /* Check for some occurrences of bad file descriptors. We only check
  151. whether fd 0, 1, or 2 are "closed". By "closed" we mean that these
  152. descriptors aren't actually closed, but are considered to be closed
  153. by this layer.
  154. Other checks are performed by the underlying OS call. */
  155. static int
  156. fdbad (int fd)
  157. {
  158. if (fd >=0 && fd <= 2 && fd_closed[fd])
  159. {
  160. errno = EBADF;
  161. return -1;
  162. }
  163. return 0;
  164. }
  165. static void
  166. do_unix_exit(os_emul_data *emul,
  167. unsigned call,
  168. const int arg0,
  169. cpu *processor,
  170. unsigned_word cia)
  171. {
  172. int status = (int)cpu_registers(processor)->gpr[arg0];
  173. if (WITH_TRACE && ppc_trace[trace_os_emul])
  174. printf_filtered ("%d)\n", status);
  175. cpu_halt(processor, cia, was_exited, status);
  176. }
  177. static void
  178. do_unix_read(os_emul_data *emul,
  179. unsigned call,
  180. const int arg0,
  181. cpu *processor,
  182. unsigned_word cia)
  183. {
  184. void *scratch_buffer;
  185. int d = (int)cpu_registers(processor)->gpr[arg0];
  186. unsigned_word buf = cpu_registers(processor)->gpr[arg0+1];
  187. int nbytes = cpu_registers(processor)->gpr[arg0+2];
  188. int status;
  189. if (WITH_TRACE && ppc_trace[trace_os_emul])
  190. printf_filtered ("%d, 0x%lx, %d", d, (long)buf, nbytes);
  191. /* get a tempoary bufer */
  192. scratch_buffer = zalloc(nbytes);
  193. /* check if buffer exists by reading it */
  194. emul_read_buffer(scratch_buffer, buf, nbytes, processor, cia);
  195. status = fdbad (d);
  196. /* read */
  197. if (status == 0)
  198. status = read (d, scratch_buffer, nbytes);
  199. emul_write_status(processor, status, errno);
  200. if (status > 0)
  201. emul_write_buffer(scratch_buffer, buf, status, processor, cia);
  202. free(scratch_buffer);
  203. }
  204. static void
  205. do_unix_write(os_emul_data *emul,
  206. unsigned call,
  207. const int arg0,
  208. cpu *processor,
  209. unsigned_word cia)
  210. {
  211. void *scratch_buffer = NULL;
  212. int d = (int)cpu_registers(processor)->gpr[arg0];
  213. unsigned_word buf = cpu_registers(processor)->gpr[arg0+1];
  214. int nbytes = cpu_registers(processor)->gpr[arg0+2];
  215. int status;
  216. if (WITH_TRACE && ppc_trace[trace_os_emul])
  217. printf_filtered ("%d, 0x%lx, %d", d, (long)buf, nbytes);
  218. /* get a tempoary bufer */
  219. scratch_buffer = zalloc(nbytes); /* FIXME - nbytes == 0 */
  220. /* copy in */
  221. emul_read_buffer(scratch_buffer, buf, nbytes,
  222. processor, cia);
  223. status = fdbad (d);
  224. /* write */
  225. if (status == 0)
  226. status = write(d, scratch_buffer, nbytes);
  227. emul_write_status(processor, status, errno);
  228. free(scratch_buffer);
  229. flush_stdoutput();
  230. }
  231. static void
  232. do_unix_open(os_emul_data *emul,
  233. unsigned call,
  234. const int arg0,
  235. cpu *processor,
  236. unsigned_word cia)
  237. {
  238. unsigned_word path_addr = cpu_registers(processor)->gpr[arg0];
  239. char path_buf[PATH_MAX];
  240. char *path = emul_read_string(path_buf, path_addr, PATH_MAX, processor, cia);
  241. int flags = (int)cpu_registers(processor)->gpr[arg0+1];
  242. int mode = (int)cpu_registers(processor)->gpr[arg0+2];
  243. int status;
  244. if (WITH_TRACE && ppc_trace[trace_os_emul])
  245. printf_filtered ("0x%lx [%s], 0x%x, 0x%x", (long)path_addr, path, flags, mode);
  246. status = open(path, flags, mode);
  247. emul_write_status(processor, status, errno);
  248. }
  249. static void
  250. do_unix_close(os_emul_data *emul,
  251. unsigned call,
  252. const int arg0,
  253. cpu *processor,
  254. unsigned_word cia)
  255. {
  256. int d = (int)cpu_registers(processor)->gpr[arg0];
  257. int status;
  258. if (WITH_TRACE && ppc_trace[trace_os_emul])
  259. printf_filtered ("%d", d);
  260. status = fdbad (d);
  261. if (status == 0)
  262. {
  263. /* Do not close stdin, stdout, or stderr. GDB may still need access to
  264. these descriptors. */
  265. if (d == 0 || d == 1 || d == 2)
  266. {
  267. fd_closed[d] = 1;
  268. status = 0;
  269. }
  270. else
  271. status = close(d);
  272. }
  273. emul_write_status(processor, status, errno);
  274. }
  275. static void
  276. do_unix_break(os_emul_data *emul,
  277. unsigned call,
  278. const int arg0,
  279. cpu *processor,
  280. unsigned_word cia)
  281. {
  282. /* just pass this onto the `vm' device */
  283. unsigned_word new_break = cpu_registers(processor)->gpr[arg0];
  284. int status;
  285. if (WITH_TRACE && ppc_trace[trace_os_emul])
  286. printf_filtered ("0x%lx", (long)cpu_registers(processor)->gpr[arg0]);
  287. status = device_ioctl(emul->vm,
  288. processor,
  289. cia,
  290. device_ioctl_break,
  291. new_break); /*ioctl-data*/
  292. emul_write_status(processor, 0, status);
  293. }
  294. #ifndef HAVE_ACCESS
  295. #define do_unix_access 0
  296. #else
  297. static void
  298. do_unix_access(os_emul_data *emul,
  299. unsigned call,
  300. const int arg0,
  301. cpu *processor,
  302. unsigned_word cia)
  303. {
  304. unsigned_word path_addr = cpu_registers(processor)->gpr[arg0];
  305. char path_buf[PATH_MAX];
  306. char *path = emul_read_string(path_buf, path_addr, PATH_MAX, processor, cia);
  307. int mode = (int)cpu_registers(processor)->gpr[arg0+1];
  308. int status;
  309. if (WITH_TRACE && ppc_trace[trace_os_emul])
  310. printf_filtered ("0x%lx [%s], 0x%x [0%o]", (long)path_addr, path, mode, mode);
  311. status = access(path, mode);
  312. emul_write_status(processor, status, errno);
  313. }
  314. #endif
  315. #ifndef HAVE_GETPID
  316. #define do_unix_getpid 0
  317. #else
  318. static void
  319. do_unix_getpid(os_emul_data *emul,
  320. unsigned call,
  321. const int arg0,
  322. cpu *processor,
  323. unsigned_word cia)
  324. {
  325. pid_t status = getpid();
  326. emul_write_status(processor, (int)status, errno);
  327. }
  328. #endif
  329. #ifndef HAVE_GETPPID
  330. #define do_unix_getppid 0
  331. #else
  332. static void
  333. do_unix_getppid(os_emul_data *emul,
  334. unsigned call,
  335. const int arg0,
  336. cpu *processor,
  337. unsigned_word cia)
  338. {
  339. pid_t status = getppid();
  340. emul_write_status(processor, (int)status, errno);
  341. }
  342. #endif
  343. #if !defined(HAVE_GETPID) || !defined(HAVE_GETPPID)
  344. #define do_unix_getpid2 0
  345. #else
  346. static void
  347. do_unix_getpid2(os_emul_data *emul,
  348. unsigned call,
  349. const int arg0,
  350. cpu *processor,
  351. unsigned_word cia)
  352. {
  353. int pid = (int)getpid();
  354. int ppid = (int)getppid();
  355. emul_write2_status(processor, pid, ppid, errno);
  356. }
  357. #endif
  358. #if !defined(HAVE_GETUID) || !defined(HAVE_GETEUID)
  359. #define do_unix_getuid2 0
  360. #else
  361. static void
  362. do_unix_getuid2(os_emul_data *emul,
  363. unsigned call,
  364. const int arg0,
  365. cpu *processor,
  366. unsigned_word cia)
  367. {
  368. uid_t uid = getuid();
  369. uid_t euid = geteuid();
  370. emul_write2_status(processor, (int)uid, (int)euid, errno);
  371. }
  372. #endif
  373. #ifndef HAVE_GETUID
  374. #define do_unix_getuid 0
  375. #else
  376. static void
  377. do_unix_getuid(os_emul_data *emul,
  378. unsigned call,
  379. const int arg0,
  380. cpu *processor,
  381. unsigned_word cia)
  382. {
  383. uid_t status = getuid();
  384. emul_write_status(processor, (int)status, errno);
  385. }
  386. #endif
  387. #ifndef HAVE_GETEUID
  388. #define do_unix_geteuid 0
  389. #else
  390. static void
  391. do_unix_geteuid(os_emul_data *emul,
  392. unsigned call,
  393. const int arg0,
  394. cpu *processor,
  395. unsigned_word cia)
  396. {
  397. uid_t status = geteuid();
  398. emul_write_status(processor, (int)status, errno);
  399. }
  400. #endif
  401. #if 0
  402. #ifndef HAVE_KILL
  403. #define do_unix_kill 0
  404. #else
  405. static void
  406. do_unix_kill(os_emul_data *emul,
  407. unsigned call,
  408. const int arg0,
  409. cpu *processor,
  410. unsigned_word cia)
  411. {
  412. pid_t pid = cpu_registers(processor)->gpr[arg0];
  413. int sig = cpu_registers(processor)->gpr[arg0+1];
  414. if (WITH_TRACE && ppc_trace[trace_os_emul])
  415. printf_filtered ("%d, %d", (int)pid, sig);
  416. printf_filtered("SYS_kill at 0x%lx - more to this than just being killed\n",
  417. (long)cia);
  418. cpu_halt(processor, cia, was_signalled, sig);
  419. }
  420. #endif
  421. #endif
  422. #ifndef HAVE_DUP
  423. #define do_unix_dup 0
  424. #else
  425. static void
  426. do_unix_dup(os_emul_data *emul,
  427. unsigned call,
  428. const int arg0,
  429. cpu *processor,
  430. unsigned_word cia)
  431. {
  432. int oldd = cpu_registers(processor)->gpr[arg0];
  433. int status = (fdbad (oldd) < 0) ? -1 : dup(oldd);
  434. int err = errno;
  435. if (WITH_TRACE && ppc_trace[trace_os_emul])
  436. printf_filtered ("%d", oldd);
  437. emul_write_status(processor, status, err);
  438. }
  439. #endif
  440. #ifndef HAVE_DUP2
  441. #define do_unix_dup2 0
  442. #else
  443. static void
  444. do_unix_dup2(os_emul_data *emul,
  445. unsigned call,
  446. const int arg0,
  447. cpu *processor,
  448. unsigned_word cia)
  449. {
  450. int oldd = cpu_registers(processor)->gpr[arg0];
  451. int newd = cpu_registers(processor)->gpr[arg0+1];
  452. int status = (fdbad (oldd) < 0) ? -1 : dup2(oldd, newd);
  453. int err = errno;
  454. if (WITH_TRACE && ppc_trace[trace_os_emul])
  455. printf_filtered ("%d, %d", oldd, newd);
  456. emul_write_status(processor, status, err);
  457. }
  458. #endif
  459. #ifndef HAVE_LSEEK
  460. #define do_unix_lseek 0
  461. #else
  462. static void
  463. do_unix_lseek(os_emul_data *emul,
  464. unsigned call,
  465. const int arg0,
  466. cpu *processor,
  467. unsigned_word cia)
  468. {
  469. int fildes = (int)cpu_registers(processor)->gpr[arg0];
  470. off_t offset = (off_t)cpu_registers(processor)->gpr[arg0+1];
  471. int whence = (int)cpu_registers(processor)->gpr[arg0+2];
  472. off_t status;
  473. if (WITH_TRACE && ppc_trace[trace_os_emul])
  474. printf_filtered ("%d %ld %d", fildes, (long)offset, whence);
  475. status = fdbad (fildes);
  476. if (status == 0)
  477. status = lseek(fildes, offset, whence);
  478. emul_write_status(processor, (int)status, errno);
  479. }
  480. #endif
  481. #if !defined(HAVE_GETGID) || !defined(HAVE_GETEGID)
  482. #define do_unix_getgid2 0
  483. #else
  484. static void
  485. do_unix_getgid2(os_emul_data *emul,
  486. unsigned call,
  487. const int arg0,
  488. cpu *processor,
  489. unsigned_word cia)
  490. {
  491. gid_t gid = getgid();
  492. gid_t egid = getegid();
  493. emul_write2_status(processor, (int)gid, (int)egid, errno);
  494. }
  495. #endif
  496. #ifndef HAVE_GETGID
  497. #define do_unix_getgid 0
  498. #else
  499. static void
  500. do_unix_getgid(os_emul_data *emul,
  501. unsigned call,
  502. const int arg0,
  503. cpu *processor,
  504. unsigned_word cia)
  505. {
  506. gid_t status = getgid();
  507. emul_write_status(processor, (int)status, errno);
  508. }
  509. #endif
  510. #ifndef HAVE_GETEGID
  511. #define do_unix_getegid 0
  512. #else
  513. static void
  514. do_unix_getegid(os_emul_data *emul,
  515. unsigned call,
  516. const int arg0,
  517. cpu *processor,
  518. unsigned_word cia)
  519. {
  520. gid_t status = getegid();
  521. emul_write_status(processor, (int)status, errno);
  522. }
  523. #endif
  524. #ifndef HAVE_UMASK
  525. #define do_unix_umask 0
  526. #else
  527. static void
  528. do_unix_umask(os_emul_data *emul,
  529. unsigned call,
  530. const int arg0,
  531. cpu *processor,
  532. unsigned_word cia)
  533. {
  534. mode_t mask = (mode_t)cpu_registers(processor)->gpr[arg0];
  535. int status = umask(mask);
  536. if (WITH_TRACE && ppc_trace[trace_os_emul])
  537. printf_filtered ("0%o", (unsigned int)mask);
  538. emul_write_status(processor, status, errno);
  539. }
  540. #endif
  541. #ifndef HAVE_CHDIR
  542. #define do_unix_chdir 0
  543. #else
  544. static void
  545. do_unix_chdir(os_emul_data *emul,
  546. unsigned call,
  547. const int arg0,
  548. cpu *processor,
  549. unsigned_word cia)
  550. {
  551. unsigned_word path_addr = cpu_registers(processor)->gpr[arg0];
  552. char path_buf[PATH_MAX];
  553. char *path = emul_read_string(path_buf, path_addr, PATH_MAX, processor, cia);
  554. int status;
  555. if (WITH_TRACE && ppc_trace[trace_os_emul])
  556. printf_filtered ("0x%lx [%s]", (long)path_addr, path);
  557. status = chdir(path);
  558. emul_write_status(processor, status, errno);
  559. }
  560. #endif
  561. #ifndef HAVE_LINK
  562. #define do_unix_link 0
  563. #else
  564. static void
  565. do_unix_link(os_emul_data *emul,
  566. unsigned call,
  567. const int arg0,
  568. cpu *processor,
  569. unsigned_word cia)
  570. {
  571. unsigned_word path1_addr = cpu_registers(processor)->gpr[arg0];
  572. char path1_buf[PATH_MAX];
  573. char *path1 = emul_read_string(path1_buf, path1_addr, PATH_MAX, processor, cia);
  574. unsigned_word path2_addr = cpu_registers(processor)->gpr[arg0+1];
  575. char path2_buf[PATH_MAX];
  576. char *path2 = emul_read_string(path2_buf, path2_addr, PATH_MAX, processor, cia);
  577. int status;
  578. if (WITH_TRACE && ppc_trace[trace_os_emul])
  579. printf_filtered ("0x%lx [%s], 0x%lx [%s]", (long)path1_addr, path1, (long)path2_addr, path2);
  580. status = link(path1, path2);
  581. emul_write_status(processor, status, errno);
  582. }
  583. #endif
  584. #ifndef HAVE_SYMLINK
  585. #define do_unix_symlink 0
  586. #else
  587. static void
  588. do_unix_symlink(os_emul_data *emul,
  589. unsigned call,
  590. const int arg0,
  591. cpu *processor,
  592. unsigned_word cia)
  593. {
  594. unsigned_word path1_addr = cpu_registers(processor)->gpr[arg0];
  595. char path1_buf[PATH_MAX];
  596. char *path1 = emul_read_string(path1_buf, path1_addr, PATH_MAX, processor, cia);
  597. unsigned_word path2_addr = cpu_registers(processor)->gpr[arg0+1];
  598. char path2_buf[PATH_MAX];
  599. char *path2 = emul_read_string(path2_buf, path2_addr, PATH_MAX, processor, cia);
  600. int status;
  601. if (WITH_TRACE && ppc_trace[trace_os_emul])
  602. printf_filtered ("0x%lx [%s], 0x%lx [%s]", (long)path1_addr, path1, (long)path2_addr, path2);
  603. status = symlink(path1, path2);
  604. emul_write_status(processor, status, errno);
  605. }
  606. #endif
  607. #ifndef HAVE_UNLINK
  608. #define do_unix_unlink 0
  609. #else
  610. static void
  611. do_unix_unlink(os_emul_data *emul,
  612. unsigned call,
  613. const int arg0,
  614. cpu *processor,
  615. unsigned_word cia)
  616. {
  617. unsigned_word path_addr = cpu_registers(processor)->gpr[arg0];
  618. char path_buf[PATH_MAX];
  619. char *path = emul_read_string(path_buf, path_addr, PATH_MAX, processor, cia);
  620. int status;
  621. if (WITH_TRACE && ppc_trace[trace_os_emul])
  622. printf_filtered ("0x%lx [%s]", (long)path_addr, path);
  623. status = unlink(path);
  624. emul_write_status(processor, status, errno);
  625. }
  626. #endif
  627. #ifndef HAVE_MKDIR
  628. #define do_unix_mkdir 0
  629. #else
  630. static void
  631. do_unix_mkdir(os_emul_data *emul,
  632. unsigned call,
  633. const int arg0,
  634. cpu *processor,
  635. unsigned_word cia)
  636. {
  637. unsigned_word path_addr = cpu_registers(processor)->gpr[arg0];
  638. char path_buf[PATH_MAX];
  639. char *path = emul_read_string(path_buf, path_addr, PATH_MAX, processor, cia);
  640. int mode = (int)cpu_registers(processor)->gpr[arg0+1];
  641. int status;
  642. if (WITH_TRACE && ppc_trace[trace_os_emul])
  643. printf_filtered ("0x%lx [%s], 0%3o", (long)path_addr, path, mode);
  644. #ifdef USE_WIN32API
  645. status = mkdir(path);
  646. #else
  647. status = mkdir(path, mode);
  648. #endif
  649. emul_write_status(processor, status, errno);
  650. }
  651. #endif
  652. #ifndef HAVE_RMDIR
  653. #define do_unix_rmdir 0
  654. #else
  655. static void
  656. do_unix_rmdir(os_emul_data *emul,
  657. unsigned call,
  658. const int arg0,
  659. cpu *processor,
  660. unsigned_word cia)
  661. {
  662. unsigned_word path_addr = cpu_registers(processor)->gpr[arg0];
  663. char path_buf[PATH_MAX];
  664. char *path = emul_read_string(path_buf, path_addr, PATH_MAX, processor, cia);
  665. int status;
  666. if (WITH_TRACE && ppc_trace[trace_os_emul])
  667. printf_filtered ("0x%lx [%s]", (long)path_addr, path);
  668. status = rmdir(path);
  669. emul_write_status(processor, status, errno);
  670. }
  671. #endif
  672. #ifndef HAVE_TIME
  673. #define do_unix_time 0
  674. #else
  675. static void
  676. do_unix_time(os_emul_data *emul,
  677. unsigned call,
  678. const int arg0,
  679. cpu *processor,
  680. unsigned_word cia)
  681. {
  682. unsigned_word tp = cpu_registers(processor)->gpr[arg0];
  683. time_t now = time ((time_t *)0);
  684. unsigned_word status = H2T_4(now);
  685. if (WITH_TRACE && ppc_trace[trace_os_emul])
  686. printf_filtered ("0x%lx", (long)tp);
  687. emul_write_status(processor, (int)status, errno);
  688. if (tp)
  689. emul_write_buffer(&status, tp, sizeof(status), processor, cia);
  690. }
  691. #endif
  692. #if !defined(HAVE_GETTIMEOFDAY)
  693. #define do_unix_gettimeofday 0
  694. #else
  695. static void
  696. do_unix_gettimeofday(os_emul_data *emul,
  697. unsigned call,
  698. const int arg0,
  699. cpu *processor,
  700. unsigned_word cia)
  701. {
  702. unsigned_word tv = cpu_registers(processor)->gpr[arg0];
  703. unsigned_word tz = cpu_registers(processor)->gpr[arg0+1];
  704. struct unix_timeval target_timeval;
  705. struct timeval host_timeval;
  706. struct unix_timezone target_timezone;
  707. struct timezone host_timezone;
  708. int status;
  709. if (WITH_TRACE && ppc_trace[trace_os_emul])
  710. printf_filtered ("0x%lx, 0x%lx", (long)tv, (long)tz);
  711. /* Just in case the system doesn't set the timezone structure */
  712. host_timezone.tz_minuteswest = 0;
  713. host_timezone.tz_dsttime = 0;
  714. status = gettimeofday(&host_timeval, &host_timezone);
  715. if (status >= 0) {
  716. if (tv) {
  717. target_timeval.tv_sec = H2T_4(host_timeval.tv_sec);
  718. target_timeval.tv_usec = H2T_4(host_timeval.tv_usec);
  719. emul_write_buffer((void *) &target_timeval, tv, sizeof(target_timeval), processor, cia);
  720. }
  721. if (tz) {
  722. target_timezone.tz_minuteswest = H2T_4(host_timezone.tz_minuteswest);
  723. target_timezone.tz_dsttime = H2T_4(host_timezone.tz_dsttime);
  724. emul_write_buffer((void *) &target_timezone, tv, sizeof(target_timezone), processor, cia);
  725. }
  726. }
  727. emul_write_status(processor, (int)status, errno);
  728. }
  729. #endif
  730. #ifndef HAVE_GETRUSAGE
  731. #define do_unix_getrusage 0
  732. #else
  733. static void
  734. do_unix_getrusage(os_emul_data *emul,
  735. unsigned call,
  736. const int arg0,
  737. cpu *processor,
  738. unsigned_word cia)
  739. {
  740. signed_word who = (signed_word)cpu_registers(processor)->gpr[arg0];
  741. unsigned_word usage = cpu_registers(processor)->gpr[arg0+1];
  742. struct rusage host_rusage, host_rusage2;
  743. struct unix_rusage target_rusage;
  744. int status;
  745. if (WITH_TRACE && ppc_trace[trace_os_emul])
  746. printf_filtered ("%ld, 0x%lx", (long)who, (long)usage);
  747. switch (who) {
  748. default:
  749. status = -1;
  750. errno = EINVAL;
  751. break;
  752. case UNIX_RUSAGE_SELF:
  753. status = getrusage(RUSAGE_SELF, &host_rusage);
  754. break;
  755. case UNIX_RUSAGE_CHILDREN:
  756. status = getrusage(RUSAGE_CHILDREN, &host_rusage);
  757. break;
  758. case UNIX_RUSAGE_BOTH:
  759. status = getrusage(RUSAGE_SELF, &host_rusage);
  760. if (status >= 0) {
  761. status = getrusage(RUSAGE_CHILDREN, &host_rusage2);
  762. if (status >= 0) {
  763. host_rusage.ru_utime.tv_sec += host_rusage2.ru_utime.tv_sec;
  764. host_rusage.ru_utime.tv_usec += host_rusage2.ru_utime.tv_usec;
  765. host_rusage.ru_stime.tv_sec += host_rusage2.ru_stime.tv_sec;
  766. host_rusage.ru_stime.tv_usec += host_rusage2.ru_stime.tv_usec;
  767. host_rusage.ru_maxrss += host_rusage2.ru_maxrss;
  768. host_rusage.ru_ixrss += host_rusage2.ru_ixrss;
  769. host_rusage.ru_idrss += host_rusage2.ru_idrss;
  770. host_rusage.ru_isrss += host_rusage2.ru_isrss;
  771. host_rusage.ru_minflt += host_rusage2.ru_minflt;
  772. host_rusage.ru_majflt += host_rusage2.ru_majflt;
  773. host_rusage.ru_nswap += host_rusage2.ru_nswap;
  774. host_rusage.ru_inblock += host_rusage2.ru_inblock;
  775. host_rusage.ru_oublock += host_rusage2.ru_oublock;
  776. host_rusage.ru_msgsnd += host_rusage2.ru_msgsnd;
  777. host_rusage.ru_msgrcv += host_rusage2.ru_msgrcv;
  778. host_rusage.ru_nsignals += host_rusage2.ru_nsignals;
  779. host_rusage.ru_nvcsw += host_rusage2.ru_nvcsw;
  780. host_rusage.ru_nivcsw += host_rusage2.ru_nivcsw;
  781. }
  782. }
  783. }
  784. if (status >= 0) {
  785. target_rusage.ru_utime.tv_sec = H2T_4(host_rusage2.ru_utime.tv_sec);
  786. target_rusage.ru_utime.tv_usec = H2T_4(host_rusage2.ru_utime.tv_usec);
  787. target_rusage.ru_stime.tv_sec = H2T_4(host_rusage2.ru_stime.tv_sec);
  788. target_rusage.ru_stime.tv_usec = H2T_4(host_rusage2.ru_stime.tv_usec);
  789. target_rusage.ru_maxrss = H2T_4(host_rusage2.ru_maxrss);
  790. target_rusage.ru_ixrss = H2T_4(host_rusage2.ru_ixrss);
  791. target_rusage.ru_idrss = H2T_4(host_rusage2.ru_idrss);
  792. target_rusage.ru_isrss = H2T_4(host_rusage2.ru_isrss);
  793. target_rusage.ru_minflt = H2T_4(host_rusage2.ru_minflt);
  794. target_rusage.ru_majflt = H2T_4(host_rusage2.ru_majflt);
  795. target_rusage.ru_nswap = H2T_4(host_rusage2.ru_nswap);
  796. target_rusage.ru_inblock = H2T_4(host_rusage2.ru_inblock);
  797. target_rusage.ru_oublock = H2T_4(host_rusage2.ru_oublock);
  798. target_rusage.ru_msgsnd = H2T_4(host_rusage2.ru_msgsnd);
  799. target_rusage.ru_msgrcv = H2T_4(host_rusage2.ru_msgrcv);
  800. target_rusage.ru_nsignals = H2T_4(host_rusage2.ru_nsignals);
  801. target_rusage.ru_nvcsw = H2T_4(host_rusage2.ru_nvcsw);
  802. target_rusage.ru_nivcsw = H2T_4(host_rusage2.ru_nivcsw);
  803. emul_write_buffer((void *) &target_rusage, usage, sizeof(target_rusage), processor, cia);
  804. }
  805. emul_write_status(processor, status, errno);
  806. }
  807. #endif
  808. static void
  809. do_unix_nop(os_emul_data *emul,
  810. unsigned call,
  811. const int arg0,
  812. cpu *processor,
  813. unsigned_word cia)
  814. {
  815. if (WITH_TRACE && ppc_trace[trace_os_emul])
  816. printf_filtered ("0x%lx 0x%lx 0x%lx 0x%lx 0x%lx 0x%lx",
  817. (long)cpu_registers(processor)->gpr[arg0],
  818. (long)cpu_registers(processor)->gpr[arg0+1],
  819. (long)cpu_registers(processor)->gpr[arg0+2],
  820. (long)cpu_registers(processor)->gpr[arg0+3],
  821. (long)cpu_registers(processor)->gpr[arg0+4],
  822. (long)cpu_registers(processor)->gpr[arg0+5]);
  823. emul_write_status(processor, 0, errno);
  824. }
  825. /* Common code for initializing the system call stuff */
  826. static os_emul_data *
  827. emul_unix_create(device *root,
  828. bfd *image,
  829. const char *name,
  830. emul_syscall *syscall)
  831. {
  832. unsigned_word top_of_stack;
  833. unsigned stack_size;
  834. int elf_binary;
  835. os_emul_data *data;
  836. device *vm;
  837. char *filename;
  838. /* merge any emulation specific entries into the device tree */
  839. /* establish a few defaults */
  840. if (image->xvec->flavour == bfd_target_elf_flavour) {
  841. elf_binary = 1;
  842. top_of_stack = 0xe0000000;
  843. stack_size = 0x00100000;
  844. }
  845. else {
  846. elf_binary = 0;
  847. top_of_stack = 0x20000000;
  848. stack_size = 0x00100000;
  849. }
  850. /* options */
  851. emul_add_tree_options(root, image, name,
  852. (WITH_ENVIRONMENT == USER_ENVIRONMENT
  853. ? "user" : "virtual"),
  854. 0 /*oea-interrupt-prefix*/);
  855. /* virtual memory - handles growth of stack/heap */
  856. vm = tree_parse(root, "/openprom/vm@0x%lx",
  857. (unsigned long)(top_of_stack - stack_size));
  858. tree_parse(vm, "./stack-base 0x%lx",
  859. (unsigned long)(top_of_stack - stack_size));
  860. tree_parse(vm, "./nr-bytes 0x%x", stack_size);
  861. filename = tree_quote_property (bfd_get_filename(image));
  862. tree_parse(root, "/openprom/vm/map-binary/file-name %s",
  863. filename);
  864. free (filename);
  865. /* finish the init */
  866. tree_parse(root, "/openprom/init/register/pc 0x%lx",
  867. (unsigned long)bfd_get_start_address(image));
  868. tree_parse(root, "/openprom/init/register/sp 0x%lx",
  869. (unsigned long)top_of_stack);
  870. tree_parse(root, "/openprom/init/register/msr 0x%x",
  871. ((tree_find_boolean_property(root, "/options/little-endian?")
  872. ? msr_little_endian_mode
  873. : 0)
  874. | (tree_find_boolean_property(root, "/openprom/options/floating-point?")
  875. ? (msr_floating_point_available
  876. | msr_floating_point_exception_mode_0
  877. | msr_floating_point_exception_mode_1)
  878. : 0)));
  879. tree_parse(root, "/openprom/init/stack/stack-type %s",
  880. (elf_binary ? "ppc-elf" : "ppc-xcoff"));
  881. /* finally our emulation data */
  882. data = ZALLOC(os_emul_data);
  883. data->vm = vm;
  884. data->syscalls = syscall;
  885. return data;
  886. }
  887. /* EMULATION
  888. Solaris - Emulation of user programs for Solaris/PPC
  889. DESCRIPTION
  890. */
  891. /* Solaris specific implementation */
  892. typedef int32_t solaris_uid_t;
  893. typedef int32_t solaris_gid_t;
  894. typedef int32_t solaris_off_t;
  895. typedef int32_t solaris_pid_t;
  896. typedef int32_t solaris_time_t;
  897. typedef uint32_t solaris_dev_t;
  898. typedef uint32_t solaris_ino_t;
  899. typedef uint32_t solaris_mode_t;
  900. typedef uint32_t solaris_nlink_t;
  901. #ifdef HAVE_SYS_STAT_H
  902. #define SOLARIS_ST_FSTYPSZ 16 /* array size for file system type name */
  903. /* AIX 7.1 defines st_pad[123] to st_[amc]tim.tv_pad, respectively */
  904. #undef st_pad1
  905. #undef st_pad2
  906. #undef st_pad3
  907. struct solaris_stat {
  908. solaris_dev_t st_dev;
  909. int32_t st_pad1[3]; /* reserved for network id */
  910. solaris_ino_t st_ino;
  911. solaris_mode_t st_mode;
  912. solaris_nlink_t st_nlink;
  913. solaris_uid_t st_uid;
  914. solaris_gid_t st_gid;
  915. solaris_dev_t st_rdev;
  916. int32_t st_pad2[2];
  917. solaris_off_t st_size;
  918. int32_t st_pad3; /* future off_t expansion */
  919. struct unix_timeval st_atim;
  920. struct unix_timeval st_mtim;
  921. struct unix_timeval st_ctim;
  922. int32_t st_blksize;
  923. int32_t st_blocks;
  924. char st_fstype[SOLARIS_ST_FSTYPSZ];
  925. int32_t st_pad4[8]; /* expansion area */
  926. };
  927. /* Convert from host stat structure to solaris stat structure */
  928. STATIC_INLINE_EMUL_UNIX void
  929. convert_to_solaris_stat(unsigned_word addr,
  930. struct stat *host,
  931. cpu *processor,
  932. unsigned_word cia)
  933. {
  934. struct solaris_stat target;
  935. int i;
  936. target.st_dev = H2T_4(host->st_dev);
  937. target.st_ino = H2T_4(host->st_ino);
  938. target.st_mode = H2T_4(host->st_mode);
  939. target.st_nlink = H2T_4(host->st_nlink);
  940. target.st_uid = H2T_4(host->st_uid);
  941. target.st_gid = H2T_4(host->st_gid);
  942. target.st_size = H2T_4(host->st_size);
  943. #ifdef HAVE_ST_RDEV
  944. target.st_rdev = H2T_4(host->st_rdev);
  945. #else
  946. target.st_rdev = 0;
  947. #endif
  948. #ifdef HAVE_ST_BLKSIZE
  949. target.st_blksize = H2T_4(host->st_blksize);
  950. #else
  951. target.st_blksize = 0;
  952. #endif
  953. #ifdef HAVE_ST_BLOCKS
  954. target.st_blocks = H2T_4(host->st_blocks);
  955. #else
  956. target.st_blocks = 0;
  957. #endif
  958. target.st_atim.tv_sec = H2T_4(host->st_atime);
  959. target.st_atim.tv_usec = 0;
  960. target.st_ctim.tv_sec = H2T_4(host->st_ctime);
  961. target.st_ctim.tv_usec = 0;
  962. target.st_mtim.tv_sec = H2T_4(host->st_mtime);
  963. target.st_mtim.tv_usec = 0;
  964. for (i = 0; i < ARRAY_SIZE (target.st_pad1); i++)
  965. target.st_pad1[i] = 0;
  966. for (i = 0; i < ARRAY_SIZE (target.st_pad2); i++)
  967. target.st_pad2[i] = 0;
  968. target.st_pad3 = 0;
  969. for (i = 0; i < ARRAY_SIZE (target.st_pad4); i++)
  970. target.st_pad4[i] = 0;
  971. /* For now, just punt and always say it is a ufs file */
  972. strcpy (target.st_fstype, "ufs");
  973. emul_write_buffer(&target, addr, sizeof(target), processor, cia);
  974. }
  975. #endif /* HAVE_SYS_STAT_H */
  976. #ifndef HAVE_STAT
  977. #define do_solaris_stat 0
  978. #else
  979. static void
  980. do_solaris_stat(os_emul_data *emul,
  981. unsigned call,
  982. const int arg0,
  983. cpu *processor,
  984. unsigned_word cia)
  985. {
  986. unsigned_word path_addr = cpu_registers(processor)->gpr[arg0];
  987. unsigned_word stat_pkt = cpu_registers(processor)->gpr[arg0+1];
  988. char path_buf[PATH_MAX];
  989. struct stat buf;
  990. char *path = emul_read_string(path_buf, path_addr, PATH_MAX, processor, cia);
  991. int status;
  992. if (WITH_TRACE && ppc_trace[trace_os_emul])
  993. printf_filtered ("0x%lx [%s], 0x%lx", (long)path_addr, path, (long)stat_pkt);
  994. status = stat (path, &buf);
  995. if (status == 0)
  996. convert_to_solaris_stat (stat_pkt, &buf, processor, cia);
  997. emul_write_status(processor, status, errno);
  998. }
  999. #endif
  1000. #ifndef HAVE_LSTAT
  1001. #define do_solaris_lstat 0
  1002. #else
  1003. static void
  1004. do_solaris_lstat(os_emul_data *emul,
  1005. unsigned call,
  1006. const int arg0,
  1007. cpu *processor,
  1008. unsigned_word cia)
  1009. {
  1010. unsigned_word path_addr = cpu_registers(processor)->gpr[arg0];
  1011. unsigned_word stat_pkt = cpu_registers(processor)->gpr[arg0+1];
  1012. char path_buf[PATH_MAX];
  1013. struct stat buf;
  1014. char *path = emul_read_string(path_buf, path_addr, PATH_MAX, processor, cia);
  1015. int status;
  1016. if (WITH_TRACE && ppc_trace[trace_os_emul])
  1017. printf_filtered ("0x%lx [%s], 0x%lx", (long)path_addr, path, (long)stat_pkt);
  1018. status = lstat (path, &buf);
  1019. if (status == 0)
  1020. convert_to_solaris_stat (stat_pkt, &buf, processor, cia);
  1021. emul_write_status(processor, status, errno);
  1022. }
  1023. #endif
  1024. #ifndef HAVE_FSTAT
  1025. #define do_solaris_fstat 0
  1026. #else
  1027. static void
  1028. do_solaris_fstat(os_emul_data *emul,
  1029. unsigned call,
  1030. const int arg0,
  1031. cpu *processor,
  1032. unsigned_word cia)
  1033. {
  1034. int fildes = (int)cpu_registers(processor)->gpr[arg0];
  1035. unsigned_word stat_pkt = cpu_registers(processor)->gpr[arg0+1];
  1036. struct stat buf;
  1037. int status;
  1038. if (WITH_TRACE && ppc_trace[trace_os_emul])
  1039. printf_filtered ("%d, 0x%lx", fildes, (long)stat_pkt);
  1040. status = fdbad (fildes);
  1041. if (status == 0)
  1042. status = fstat (fildes, &buf);
  1043. if (status == 0)
  1044. convert_to_solaris_stat (stat_pkt, &buf, processor, cia);
  1045. emul_write_status(processor, status, errno);
  1046. }
  1047. #endif
  1048. #if defined(HAVE_TERMIO_STRUCTURE) || defined(HAVE_TERMIOS_STRUCTURE)
  1049. #define SOLARIS_TIOC ('T'<<8)
  1050. #define SOLARIS_NCC 8
  1051. #define SOLARIS_NCCS 19
  1052. #define SOLARIS_VINTR 0
  1053. #define SOLARIS_VQUIT 1
  1054. #define SOLARIS_VERASE 2
  1055. #define SOLARIS_VKILL 3
  1056. #define SOLARIS_VEOF 4
  1057. #define SOLARIS_VEOL 5
  1058. #define SOLARIS_VEOL2 6
  1059. #define SOLARIS_VSWTCH 7
  1060. #define SOLARIS_VSTART 8
  1061. #define SOLARIS_VSTOP 9
  1062. #define SOLARIS_VSUSP 10
  1063. #define SOLARIS_VDSUSP 11
  1064. #define SOLARIS_VREPRINT 12
  1065. #define SOLARIS_VDISCARD 13
  1066. #define SOLARIS_VWERASE 14
  1067. #define SOLARIS_VLNEXT 15
  1068. #endif
  1069. #if defined(HAVE_TERMIO_STRUCTURE) || defined(HAVE_TERMIOS_STRUCTURE)
  1070. /* Convert to/from host termio structure */
  1071. struct solaris_termio {
  1072. uint16_t c_iflag; /* input modes */
  1073. uint16_t c_oflag; /* output modes */
  1074. uint16_t c_cflag; /* control modes */
  1075. uint16_t c_lflag; /* line discipline modes */
  1076. uint8_t c_line; /* line discipline */
  1077. uint8_t c_cc[SOLARIS_NCC]; /* control chars */
  1078. };
  1079. STATIC_INLINE_EMUL_UNIX void
  1080. convert_to_solaris_termio(unsigned_word addr,
  1081. struct termio *host,
  1082. cpu *processor,
  1083. unsigned_word cia)
  1084. {
  1085. struct solaris_termio target;
  1086. int i;
  1087. target.c_iflag = H2T_2 (host->c_iflag);
  1088. target.c_oflag = H2T_2 (host->c_oflag);
  1089. target.c_cflag = H2T_2 (host->c_cflag);
  1090. target.c_lflag = H2T_2 (host->c_lflag);
  1091. #if defined(HAVE_TERMIO_CLINE) || defined(HAVE_TERMIOS_CLINE)
  1092. target.c_line = host->c_line;
  1093. #else
  1094. target.c_line = 0;
  1095. #endif
  1096. for (i = 0; i < SOLARIS_NCC; i++)
  1097. target.c_cc[i] = 0;
  1098. #ifdef VINTR
  1099. target.c_cc[SOLARIS_VINTR] = host->c_cc[VINTR];
  1100. #endif
  1101. #ifdef VQUIT
  1102. target.c_cc[SOLARIS_VQUIT] = host->c_cc[VQUIT];
  1103. #endif
  1104. #ifdef VERASE
  1105. target.c_cc[SOLARIS_VERASE] = host->c_cc[VERASE];
  1106. #endif
  1107. #ifdef VKILL
  1108. target.c_cc[SOLARIS_VKILL] = host->c_cc[VKILL];
  1109. #endif
  1110. #ifdef VEOF
  1111. target.c_cc[SOLARIS_VEOF] = host->c_cc[VEOF];
  1112. #endif
  1113. #ifdef VEOL
  1114. target.c_cc[SOLARIS_VEOL] = host->c_cc[VEOL];
  1115. #endif
  1116. #ifdef VEOL2
  1117. target.c_cc[SOLARIS_VEOL2] = host->c_cc[VEOL2];
  1118. #endif
  1119. #ifdef VSWTCH
  1120. target.c_cc[SOLARIS_VSWTCH] = host->c_cc[VSWTCH];
  1121. #else
  1122. #ifdef VSWTC
  1123. target.c_cc[SOLARIS_VSWTCH] = host->c_cc[VSWTC];
  1124. #endif
  1125. #endif
  1126. emul_write_buffer(&target, addr, sizeof(target), processor, cia);
  1127. }
  1128. #endif /* HAVE_TERMIO_STRUCTURE || HAVE_TERMIOS_STRUCTURE */
  1129. #ifdef HAVE_TERMIOS_STRUCTURE
  1130. /* Convert to/from host termios structure */
  1131. typedef uint32_t solaris_tcflag_t;
  1132. typedef uint8_t solaris_cc_t;
  1133. typedef uint32_t solaris_speed_t;
  1134. struct solaris_termios {
  1135. solaris_tcflag_t c_iflag;
  1136. solaris_tcflag_t c_oflag;
  1137. solaris_tcflag_t c_cflag;
  1138. solaris_tcflag_t c_lflag;
  1139. solaris_cc_t c_cc[SOLARIS_NCCS];
  1140. };
  1141. STATIC_INLINE_EMUL_UNIX void
  1142. convert_to_solaris_termios(unsigned_word addr,
  1143. struct termios *host,
  1144. cpu *processor,
  1145. unsigned_word cia)
  1146. {
  1147. struct solaris_termios target;
  1148. int i;
  1149. target.c_iflag = H2T_4 (host->c_iflag);
  1150. target.c_oflag = H2T_4 (host->c_oflag);
  1151. target.c_cflag = H2T_4 (host->c_cflag);
  1152. target.c_lflag = H2T_4 (host->c_lflag);
  1153. for (i = 0; i < SOLARIS_NCCS; i++)
  1154. target.c_cc[i] = 0;
  1155. #ifdef VINTR
  1156. target.c_cc[SOLARIS_VINTR] = host->c_cc[VINTR];
  1157. #endif
  1158. #ifdef VQUIT
  1159. target.c_cc[SOLARIS_VQUIT] = host->c_cc[VQUIT];
  1160. #endif
  1161. #ifdef VERASE
  1162. target.c_cc[SOLARIS_VERASE] = host->c_cc[VERASE];
  1163. #endif
  1164. #ifdef VKILL
  1165. target.c_cc[SOLARIS_VKILL] = host->c_cc[VKILL];
  1166. #endif
  1167. #ifdef VEOF
  1168. target.c_cc[SOLARIS_VEOF] = host->c_cc[VEOF];
  1169. #endif
  1170. #ifdef VEOL
  1171. target.c_cc[SOLARIS_VEOL] = host->c_cc[VEOL];
  1172. #endif
  1173. #ifdef VEOL2
  1174. target.c_cc[SOLARIS_VEOL2] = host->c_cc[VEOL2];
  1175. #endif
  1176. #ifdef VSWTCH
  1177. target.c_cc[SOLARIS_VSWTCH] = host->c_cc[VSWTCH];
  1178. #else
  1179. #ifdef VSWTC
  1180. target.c_cc[SOLARIS_VSWTCH] = host->c_cc[VSWTC];
  1181. #endif
  1182. #endif
  1183. #ifdef VSTART
  1184. target.c_cc[SOLARIS_VSTART] = host->c_cc[VSTART];
  1185. #endif
  1186. #ifdef VSTOP
  1187. target.c_cc[SOLARIS_VSTOP] = host->c_cc[VSTOP];
  1188. #endif
  1189. #ifdef VSUSP
  1190. target.c_cc[SOLARIS_VSUSP] = host->c_cc[VSUSP];
  1191. #endif
  1192. #ifdef VDSUSP
  1193. target.c_cc[SOLARIS_VDSUSP] = host->c_cc[VDSUSP];
  1194. #endif
  1195. #ifdef VREPRINT
  1196. target.c_cc[SOLARIS_VREPRINT] = host->c_cc[VREPRINT];
  1197. #endif
  1198. #ifdef VDISCARD
  1199. target.c_cc[SOLARIS_VDISCARD] = host->c_cc[VDISCARD];
  1200. #endif
  1201. #ifdef VWERASE
  1202. target.c_cc[SOLARIS_VWERASE] = host->c_cc[VWERASE];
  1203. #endif
  1204. #ifdef VLNEXT
  1205. target.c_cc[SOLARIS_VLNEXT] = host->c_cc[VLNEXT];
  1206. #endif
  1207. emul_write_buffer(&target, addr, sizeof(target), processor, cia);
  1208. }
  1209. #endif /* HAVE_TERMIOS_STRUCTURE */
  1210. #ifndef HAVE_IOCTL
  1211. #define do_solaris_ioctl 0
  1212. #else
  1213. static void
  1214. do_solaris_ioctl(os_emul_data *emul,
  1215. unsigned call,
  1216. const int arg0,
  1217. cpu *processor,
  1218. unsigned_word cia)
  1219. {
  1220. int fildes = cpu_registers(processor)->gpr[arg0];
  1221. unsigned request = cpu_registers(processor)->gpr[arg0+1];
  1222. unsigned_word argp_addr = cpu_registers(processor)->gpr[arg0+2];
  1223. int status = 0;
  1224. const char *name = "<unknown>";
  1225. #ifdef HAVE_TERMIOS_STRUCTURE
  1226. struct termios host_termio;
  1227. #else
  1228. #ifdef HAVE_TERMIO_STRUCTURE
  1229. struct termio host_termio;
  1230. #endif
  1231. #endif
  1232. status = fdbad (fildes);
  1233. if (status != 0)
  1234. goto done;
  1235. switch (request)
  1236. {
  1237. case 0: /* make sure we have at least one case */
  1238. default:
  1239. status = -1;
  1240. errno = EINVAL;
  1241. break;
  1242. #if defined(HAVE_TERMIO_STRUCTURE) || defined(HAVE_TERMIOS_STRUCTURE)
  1243. #if defined(TCGETA) || defined(TCGETS) || defined(HAVE_TCGETATTR)
  1244. case SOLARIS_TIOC | 1: /* TCGETA */
  1245. name = "TCGETA";
  1246. #ifdef HAVE_TCGETATTR
  1247. status = tcgetattr(fildes, &host_termio);
  1248. #elif defined(TCGETS)
  1249. status = ioctl (fildes, TCGETS, &host_termio);
  1250. #else
  1251. status = ioctl (fildes, TCGETA, &host_termio);
  1252. #endif
  1253. if (status == 0)
  1254. convert_to_solaris_termio (argp_addr, &host_termio, processor, cia);
  1255. break;
  1256. #endif /* TCGETA */
  1257. #endif /* HAVE_TERMIO_STRUCTURE */
  1258. #ifdef HAVE_TERMIOS_STRUCTURE
  1259. #if defined(TCGETS) || defined(HAVE_TCGETATTR)
  1260. case SOLARIS_TIOC | 13: /* TCGETS */
  1261. name = "TCGETS";
  1262. #ifdef HAVE_TCGETATTR
  1263. status = tcgetattr(fildes, &host_termio);
  1264. #else
  1265. status = ioctl (fildes, TCGETS, &host_termio);
  1266. #endif
  1267. if (status == 0)
  1268. convert_to_solaris_termios (argp_addr, &host_termio, processor, cia);
  1269. break;
  1270. #endif /* TCGETS */
  1271. #endif /* HAVE_TERMIOS_STRUCTURE */
  1272. }
  1273. done:
  1274. emul_write_status(processor, status, errno);
  1275. if (WITH_TRACE && ppc_trace[trace_os_emul])
  1276. printf_filtered ("%d, 0x%x [%s], 0x%lx", fildes, request, name, (long)argp_addr);
  1277. }
  1278. #endif /* HAVE_IOCTL */
  1279. static emul_syscall_descriptor solaris_descriptors[] = {
  1280. /* 0 */ { 0, "syscall" },
  1281. /* 1 */ { do_unix_exit, "exit" },
  1282. /* 2 */ { 0, "fork" },
  1283. /* 3 */ { do_unix_read, "read" },
  1284. /* 4 */ { do_unix_write, "write" },
  1285. /* 5 */ { do_unix_open, "open" },
  1286. /* 6 */ { do_unix_close, "close" },
  1287. /* 7 */ { 0, "wait" },
  1288. /* 8 */ { 0, "creat" },
  1289. /* 9 */ { do_unix_link, "link" },
  1290. /* 10 */ { do_unix_unlink, "unlink" },
  1291. /* 11 */ { 0, "exec" },
  1292. /* 12 */ { do_unix_chdir, "chdir" },
  1293. /* 13 */ { do_unix_time, "time" },
  1294. /* 14 */ { 0, "mknod" },
  1295. /* 15 */ { 0, "chmod" },
  1296. /* 16 */ { 0, "chown" },
  1297. /* 17 */ { do_unix_break, "brk" },
  1298. /* 18 */ { do_solaris_stat, "stat" },
  1299. /* 19 */ { do_unix_lseek, "lseek" },
  1300. /* 20 */ { do_unix_getpid2, "getpid" },
  1301. /* 21 */ { 0, "mount" },
  1302. /* 22 */ { 0, "umount" },
  1303. /* 23 */ { 0, "setuid" },
  1304. /* 24 */ { do_unix_getuid2, "getuid" },
  1305. /* 25 */ { 0, "stime" },
  1306. /* 26 */ { 0, "ptrace" },
  1307. /* 27 */ { 0, "alarm" },
  1308. /* 28 */ { do_solaris_fstat, "fstat" },
  1309. /* 29 */ { 0, "pause" },
  1310. /* 30 */ { 0, "utime" },
  1311. /* 31 */ { 0, "stty" },
  1312. /* 32 */ { 0, "gtty" },
  1313. /* 33 */ { do_unix_access, "access" },
  1314. /* 34 */ { 0, "nice" },
  1315. /* 35 */ { 0, "statfs" },
  1316. /* 36 */ { 0, "sync" },
  1317. /* 37 */ { 0, "kill" },
  1318. /* 38 */ { 0, "fstatfs" },
  1319. /* 39 */ { 0, "pgrpsys" },
  1320. /* 40 */ { 0, "xenix" },
  1321. /* 41 */ { do_unix_dup, "dup" },
  1322. /* 42 */ { 0, "pipe" },
  1323. /* 43 */ { 0, "times" },
  1324. /* 44 */ { 0, "profil" },
  1325. /* 45 */ { 0, "plock" },
  1326. /* 46 */ { 0, "setgid" },
  1327. /* 47 */ { do_unix_getgid2, "getgid" },
  1328. /* 48 */ { 0, "signal" },
  1329. /* 49 */ { 0, "msgsys" },
  1330. /* 50 */ { 0, "syssun" },
  1331. /* 51 */ { 0, "acct" },
  1332. /* 52 */ { 0, "shmsys" },
  1333. /* 53 */ { 0, "semsys" },
  1334. /* 54 */ { do_solaris_ioctl, "ioctl" },
  1335. /* 55 */ { 0, "uadmin" },
  1336. /* 56 */ { 0, 0 /* reserved for exch */ },
  1337. /* 57 */ { 0, "utssys" },
  1338. /* 58 */ { 0, "fdsync" },
  1339. /* 59 */ { 0, "execve" },
  1340. /* 60 */ { do_unix_umask, "umask" },
  1341. /* 61 */ { 0, "chroot" },
  1342. /* 62 */ { 0, "fcntl" },
  1343. /* 63 */ { 0, "ulimit" },
  1344. /* 64 */ { 0, 0 /* reserved for UNIX PC */ },
  1345. /* 64 */ { 0, 0 /* reserved for UNIX PC */ },
  1346. /* 65 */ { 0, 0 /* reserved for UNIX PC */ },
  1347. /* 66 */ { 0, 0 /* reserved for UNIX PC */ },
  1348. /* 67 */ { 0, 0 /* reserved for UNIX PC */ },
  1349. /* 68 */ { 0, 0 /* reserved for UNIX PC */ },
  1350. /* 69 */ { 0, 0 /* reserved for UNIX PC */ },
  1351. /* 70 */ { 0, 0 /* was advfs */ },
  1352. /* 71 */ { 0, 0 /* was unadvfs */ },
  1353. /* 72 */ { 0, 0 /* was rmount */ },
  1354. /* 73 */ { 0, 0 /* was rumount */ },
  1355. /* 74 */ { 0, 0 /* was rfstart */ },
  1356. /* 75 */ { 0, 0 /* was sigret */ },
  1357. /* 76 */ { 0, 0 /* was rdebug */ },
  1358. /* 77 */ { 0, 0 /* was rfstop */ },
  1359. /* 78 */ { 0, 0 /* was rfsys */ },
  1360. /* 79 */ { do_unix_rmdir, "rmdir" },
  1361. /* 80 */ { do_unix_mkdir, "mkdir" },
  1362. /* 81 */ { 0, "getdents" },
  1363. /* 82 */ { 0, 0 /* was libattach */ },
  1364. /* 83 */ { 0, 0 /* was libdetach */ },
  1365. /* 84 */ { 0, "sysfs" },
  1366. /* 85 */ { 0, "getmsg" },
  1367. /* 86 */ { 0, "putmsg" },
  1368. /* 87 */ { 0, "poll" },
  1369. /* 88 */ { do_solaris_lstat, "lstat" },
  1370. /* 89 */ { do_unix_symlink, "symlink" },
  1371. /* 90 */ { 0, "readlink" },
  1372. /* 91 */ { 0, "setgroups" },
  1373. /* 92 */ { 0, "getgroups" },
  1374. /* 93 */ { 0, "fchmod" },
  1375. /* 94 */ { 0, "fchown" },
  1376. /* 95 */ { 0, "sigprocmask" },
  1377. /* 96 */ { 0, "sigsuspend" },
  1378. /* 97 */ { do_unix_nop, "sigaltstack" },
  1379. /* 98 */ { do_unix_nop, "sigaction" },
  1380. /* 99 */ { 0, "sigpending" },
  1381. /* 100 */ { 0, "context" },
  1382. /* 101 */ { 0, "evsys" },
  1383. /* 102 */ { 0, "evtrapret" },
  1384. /* 103 */ { 0, "statvfs" },
  1385. /* 104 */ { 0, "fstatvfs" },
  1386. /* 105 */ { 0, 0 /* reserved */ },
  1387. /* 106 */ { 0, "nfssys" },
  1388. /* 107 */ { 0, "waitsys" },
  1389. /* 108 */ { 0, "sigsendsys" },
  1390. /* 109 */ { 0, "hrtsys" },
  1391. /* 110 */ { 0, "acancel" },
  1392. /* 111 */ { 0, "async" },
  1393. /* 112 */ { 0, "priocntlsys" },
  1394. /* 113 */ { 0, "pathconf" },
  1395. /* 114 */ { 0, "mincore" },
  1396. /* 115 */ { 0, "mmap" },
  1397. /* 116 */ { 0, "mprotect" },
  1398. /* 117 */ { 0, "munmap" },
  1399. /* 118 */ { 0, "fpathconf" },
  1400. /* 119 */ { 0, "vfork" },
  1401. /* 120 */ { 0, "fchdir" },
  1402. /* 121 */ { 0, "readv" },
  1403. /* 122 */ { 0, "writev" },
  1404. /* 123 */ { 0, "xstat" },
  1405. /* 124 */ { 0, "lxstat" },
  1406. /* 125 */ { 0, "fxstat" },
  1407. /* 126 */ { 0, "xmknod" },
  1408. /* 127 */ { 0, "clocal" },
  1409. /* 128 */ { 0, "setrlimit" },
  1410. /* 129 */ { 0, "getrlimit" },
  1411. /* 130 */ { 0, "lchown" },
  1412. /* 131 */ { 0, "memcntl" },
  1413. /* 132 */ { 0, "getpmsg" },
  1414. /* 133 */ { 0, "putpmsg" },
  1415. /* 134 */ { 0, "rename" },
  1416. /* 135 */ { 0, "uname" },
  1417. /* 136 */ { 0, "setegid" },
  1418. /* 137 */ { 0, "sysconfig" },
  1419. /* 138 */ { 0, "adjtime" },
  1420. /* 139 */ { 0, "systeminfo" },
  1421. /* 140 */ { 0, 0 /* reserved */ },
  1422. /* 141 */ { 0, "seteuid" },
  1423. /* 142 */ { 0, "vtrace" },
  1424. /* 143 */ { 0, "fork1" },
  1425. /* 144 */ { 0, "sigtimedwait" },
  1426. /* 145 */ { 0, "lwp_info" },
  1427. /* 146 */ { 0, "yield" },
  1428. /* 147 */ { 0, "lwp_sema_wait" },
  1429. /* 148 */ { 0, "lwp_sema_post" },
  1430. /* 149 */ { 0, 0 /* reserved */ },
  1431. /* 150 */ { 0, 0 /* reserved */ },
  1432. /* 151 */ { 0, 0 /* reserved */ },
  1433. /* 152 */ { 0, "modctl" },
  1434. /* 153 */ { 0, "fchroot" },
  1435. /* 154 */ { 0, "utimes" },
  1436. /* 155 */ { 0, "vhangup" },
  1437. /* 156 */ { do_unix_gettimeofday, "gettimeofday" },
  1438. /* 157 */ { 0, "getitimer" },
  1439. /* 158 */ { 0, "setitimer" },
  1440. /* 159 */ { 0, "lwp_create" },
  1441. /* 160 */ { 0, "lwp_exit" },
  1442. /* 161 */ { 0, "lwp_suspend" },
  1443. /* 162 */ { 0, "lwp_continue" },
  1444. /* 163 */ { 0, "lwp_kill" },
  1445. /* 164 */ { 0, "lwp_self" },
  1446. /* 165 */ { 0, "lwp_setprivate" },
  1447. /* 166 */ { 0, "lwp_getprivate" },
  1448. /* 167 */ { 0, "lwp_wait" },
  1449. /* 168 */ { 0, "lwp_mutex_unlock" },
  1450. /* 169 */ { 0, "lwp_mutex_lock" },
  1451. /* 170 */ { 0, "lwp_cond_wait" },
  1452. /* 171 */ { 0, "lwp_cond_signal" },
  1453. /* 172 */ { 0, "lwp_cond_broadcast" },
  1454. /* 173 */ { 0, "pread" },
  1455. /* 174 */ { 0, "pwrite" },
  1456. /* 175 */ { 0, "llseek" },
  1457. /* 176 */ { 0, "inst_sync" },
  1458. /* 177 */ { 0, 0 /* reserved */ },
  1459. /* 178 */ { 0, "kaio" },
  1460. /* 179 */ { 0, 0 /* reserved */ },
  1461. /* 180 */ { 0, 0 /* reserved */ },
  1462. /* 181 */ { 0, 0 /* reserved */ },
  1463. /* 182 */ { 0, 0 /* reserved */ },
  1464. /* 183 */ { 0, 0 /* reserved */ },
  1465. /* 184 */ { 0, "tsolsys" },
  1466. /* 185 */ { 0, "acl" },
  1467. /* 186 */ { 0, "auditsys" },
  1468. /* 187 */ { 0, "processor_bind" },
  1469. /* 188 */ { 0, "processor_info" },
  1470. /* 189 */ { 0, "p_online" },
  1471. /* 190 */ { 0, "sigqueue" },
  1472. /* 191 */ { 0, "clock_gettime" },
  1473. /* 192 */ { 0, "clock_settime" },
  1474. /* 193 */ { 0, "clock_getres" },
  1475. /* 194 */ { 0, "timer_create" },
  1476. /* 195 */ { 0, "timer_delete" },
  1477. /* 196 */ { 0, "timer_settime" },
  1478. /* 197 */ { 0, "timer_gettime" },
  1479. /* 198 */ { 0, "timer_getoverrun" },
  1480. /* 199 */ { 0, "nanosleep" },
  1481. /* 200 */ { 0, "facl" },
  1482. /* 201 */ { 0, "door" },
  1483. /* 202 */ { 0, "setreuid" },
  1484. /* 203 */ { 0, "setregid" },
  1485. /* 204 */ { 0, "install_utrap" },
  1486. /* 205 */ { 0, 0 /* reserved */ },
  1487. /* 206 */ { 0, 0 /* reserved */ },
  1488. /* 207 */ { 0, 0 /* reserved */ },
  1489. /* 208 */ { 0, 0 /* reserved */ },
  1490. /* 209 */ { 0, 0 /* reserved */ },
  1491. /* 210 */ { 0, "signotifywait" },
  1492. /* 211 */ { 0, "lwp_sigredirect" },
  1493. /* 212 */ { 0, "lwp_alarm" },
  1494. };
  1495. static char *(solaris_error_names[]) = {
  1496. /* 0 */ "ESUCCESS",
  1497. /* 1 */ "EPERM",
  1498. /* 2 */ "ENOENT",
  1499. /* 3 */ "ESRCH",
  1500. /* 4 */ "EINTR",
  1501. /* 5 */ "EIO",
  1502. /* 6 */ "ENXIO",
  1503. /* 7 */ "E2BIG",
  1504. /* 8 */ "ENOEXEC",
  1505. /* 9 */ "EBADF",
  1506. /* 10 */ "ECHILD",
  1507. /* 11 */ "EAGAIN",
  1508. /* 12 */ "ENOMEM",
  1509. /* 13 */ "EACCES",
  1510. /* 14 */ "EFAULT",
  1511. /* 15 */ "ENOTBLK",
  1512. /* 16 */ "EBUSY",
  1513. /* 17 */ "EEXIST",
  1514. /* 18 */ "EXDEV",
  1515. /* 19 */ "ENODEV",
  1516. /* 20 */ "ENOTDIR",
  1517. /* 21 */ "EISDIR",
  1518. /* 22 */ "EINVAL",
  1519. /* 23 */ "ENFILE",
  1520. /* 24 */ "EMFILE",
  1521. /* 25 */ "ENOTTY",
  1522. /* 26 */ "ETXTBSY",
  1523. /* 27 */ "EFBIG",
  1524. /* 28 */ "ENOSPC",
  1525. /* 29 */ "ESPIPE",
  1526. /* 30 */ "EROFS",
  1527. /* 31 */ "EMLINK",
  1528. /* 32 */ "EPIPE",
  1529. /* 33 */ "EDOM",
  1530. /* 34 */ "ERANGE",
  1531. /* 35 */ "ENOMSG",
  1532. /* 36 */ "EIDRM",
  1533. /* 37 */ "ECHRNG",
  1534. /* 38 */ "EL2NSYNC",
  1535. /* 39 */ "EL3HLT",
  1536. /* 40 */ "EL3RST",
  1537. /* 41 */ "ELNRNG",
  1538. /* 42 */ "EUNATCH",
  1539. /* 43 */ "ENOCSI",
  1540. /* 44 */ "EL2HLT",
  1541. /* 45 */ "EDEADLK",
  1542. /* 46 */ "ENOLCK",
  1543. /* 47 */ "ECANCELED",
  1544. /* 48 */ "ENOTSUP",
  1545. /* 49 */ "EDQUOT",
  1546. /* 50 */ "EBADE",
  1547. /* 51 */ "EBADR",
  1548. /* 52 */ "EXFULL",
  1549. /* 53 */ "ENOANO",
  1550. /* 54 */ "EBADRQC",
  1551. /* 55 */ "EBADSLT",
  1552. /* 56 */ "EDEADLOCK",
  1553. /* 57 */ "EBFONT",
  1554. /* 58 */ "Error code 58",
  1555. /* 59 */ "Error code 59",
  1556. /* 60 */ "ENOSTR",
  1557. /* 61 */ "ENODATA",
  1558. /* 62 */ "ETIME",
  1559. /* 63 */ "ENOSR",
  1560. /* 64 */ "ENONET",
  1561. /* 65 */ "ENOPKG",
  1562. /* 66 */ "EREMOTE",
  1563. /* 67 */ "ENOLINK",
  1564. /* 68 */ "EADV",
  1565. /* 69 */ "ESRMNT",
  1566. /* 70 */ "ECOMM",
  1567. /* 71 */ "EPROTO",
  1568. /* 72 */ "Error code 72",
  1569. /* 73 */ "Error code 73",
  1570. /* 74 */ "EMULTIHOP",
  1571. /* 75 */ "Error code 75",
  1572. /* 76 */ "Error code 76",
  1573. /* 77 */ "EBADMSG",
  1574. /* 78 */ "ENAMETOOLONG",
  1575. /* 79 */ "EOVERFLOW",
  1576. /* 80 */ "ENOTUNIQ",
  1577. /* 81 */ "EBADFD",
  1578. /* 82 */ "EREMCHG",
  1579. /* 83 */ "ELIBACC",
  1580. /* 84 */ "ELIBBAD",
  1581. /* 85 */ "ELIBSCN",
  1582. /* 86 */ "ELIBMAX",
  1583. /* 87 */ "ELIBEXEC",
  1584. /* 88 */ "EILSEQ",
  1585. /* 89 */ "ENOSYS",
  1586. /* 90 */ "ELOOP",
  1587. /* 91 */ "ERESTART",
  1588. /* 92 */ "ESTRPIPE",
  1589. /* 93 */ "ENOTEMPTY",
  1590. /* 94 */ "EUSERS",
  1591. /* 95 */ "ENOTSOCK",
  1592. /* 96 */ "EDESTADDRREQ",
  1593. /* 97 */ "EMSGSIZE",
  1594. /* 98 */ "EPROTOTYPE",
  1595. /* 99 */ "ENOPROTOOPT",
  1596. /* 100 */ "Error code 100",
  1597. /* 101 */ "Error code 101",
  1598. /* 102 */ "Error code 102",
  1599. /* 103 */ "Error code 103",
  1600. /* 104 */ "Error code 104",
  1601. /* 105 */ "Error code 105",
  1602. /* 106 */ "Error code 106",
  1603. /* 107 */ "Error code 107",
  1604. /* 108 */ "Error code 108",
  1605. /* 109 */ "Error code 109",
  1606. /* 110 */ "Error code 110",
  1607. /* 111 */ "Error code 111",
  1608. /* 112 */ "Error code 112",
  1609. /* 113 */ "Error code 113",
  1610. /* 114 */ "Error code 114",
  1611. /* 115 */ "Error code 115",
  1612. /* 116 */ "Error code 116",
  1613. /* 117 */ "Error code 117",
  1614. /* 118 */ "Error code 118",
  1615. /* 119 */ "Error code 119",
  1616. /* 120 */ "EPROTONOSUPPORT",
  1617. /* 121 */ "ESOCKTNOSUPPORT",
  1618. /* 122 */ "EOPNOTSUPP",
  1619. /* 123 */ "EPFNOSUPPORT",
  1620. /* 124 */ "EAFNOSUPPORT",
  1621. /* 125 */ "EADDRINUSE",
  1622. /* 126 */ "EADDRNOTAVAIL",
  1623. /* 127 */ "ENETDOWN",
  1624. /* 128 */ "ENETUNREACH",
  1625. /* 129 */ "ENETRESET",
  1626. /* 130 */ "ECONNABORTED",
  1627. /* 131 */ "ECONNRESET",
  1628. /* 132 */ "ENOBUFS",
  1629. /* 133 */ "EISCONN",
  1630. /* 134 */ "ENOTCONN",
  1631. /* 135 */ "Error code 135", /* XENIX has 135 - 142 */
  1632. /* 136 */ "Error code 136",
  1633. /* 137 */ "Error code 137",
  1634. /* 138 */ "Error code 138",
  1635. /* 139 */ "Error code 139",
  1636. /* 140 */ "Error code 140",
  1637. /* 141 */ "Error code 141",
  1638. /* 142 */ "Error code 142",
  1639. /* 143 */ "ESHUTDOWN",
  1640. /* 144 */ "ETOOMANYREFS",
  1641. /* 145 */ "ETIMEDOUT",
  1642. /* 146 */ "ECONNREFUSED",
  1643. /* 147 */ "EHOSTDOWN",
  1644. /* 148 */ "EHOSTUNREACH",
  1645. /* 149 */ "EALREADY",
  1646. /* 150 */ "EINPROGRESS",
  1647. /* 151 */ "ESTALE",
  1648. };
  1649. static char *(solaris_signal_names[]) = {
  1650. /* 0 */ 0,
  1651. /* 1 */ "SIGHUP",
  1652. /* 2 */ "SIGINT",
  1653. /* 3 */ "SIGQUIT",
  1654. /* 4 */ "SIGILL",
  1655. /* 5 */ "SIGTRAP",
  1656. /* 6 */ "SIGABRT",
  1657. /* 7 */ "SIGEMT",
  1658. /* 8 */ "SIGFPE",
  1659. /* 9 */ "SIGKILL",
  1660. /* 10 */ "SIGBUS",
  1661. /* 11 */ "SIGSEGV",
  1662. /* 12 */ "SIGSYS",
  1663. /* 13 */ "SIGPIPE",
  1664. /* 14 */ "SIGALRM",
  1665. /* 15 */ "SIGTERM",
  1666. /* 16 */ "SIGUSR1",
  1667. /* 17 */ "SIGUSR2",
  1668. /* 18 */ "SIGCHLD",
  1669. /* 19 */ "SIGPWR",
  1670. /* 20 */ "SIGWINCH",
  1671. /* 21 */ "SIGURG",
  1672. /* 22 */ "SIGPOLL",
  1673. /* 23 */ "SIGSTOP",
  1674. /* 24 */ "SIGTSTP",
  1675. /* 25 */ "SIGCONT",
  1676. /* 26 */ "SIGTTIN",
  1677. /* 27 */ "SIGTTOU",
  1678. /* 28 */ "SIGVTALRM",
  1679. /* 29 */ "SIGPROF",
  1680. /* 30 */ "SIGXCPU",
  1681. /* 31 */ "SIGXFSZ",
  1682. /* 32 */ "SIGWAITING",
  1683. /* 33 */ "SIGLWP",
  1684. /* 34 */ "SIGFREEZE",
  1685. /* 35 */ "SIGTHAW",
  1686. /* 36 */ "SIGCANCEL",
  1687. };
  1688. static emul_syscall emul_solaris_syscalls = {
  1689. solaris_descriptors,
  1690. ARRAY_SIZE (solaris_descriptors),
  1691. solaris_error_names,
  1692. ARRAY_SIZE (solaris_error_names),
  1693. solaris_signal_names,
  1694. ARRAY_SIZE (solaris_signal_names),
  1695. };
  1696. /* Solaris's os_emul interface, most are just passed on to the generic
  1697. syscall stuff */
  1698. static os_emul_data *
  1699. emul_solaris_create(device *root,
  1700. bfd *image,
  1701. const char *name)
  1702. {
  1703. /* check that this emulation is really for us */
  1704. if (name != NULL && strcmp(name, "solaris") != 0)
  1705. return NULL;
  1706. if (image == NULL)
  1707. return NULL;
  1708. return emul_unix_create(root, image, "solaris", &emul_solaris_syscalls);
  1709. }
  1710. static void
  1711. emul_solaris_init(os_emul_data *emul_data,
  1712. int nr_cpus)
  1713. {
  1714. fd_closed[0] = 0;
  1715. fd_closed[1] = 0;
  1716. fd_closed[2] = 0;
  1717. }
  1718. static void
  1719. emul_solaris_system_call(cpu *processor,
  1720. unsigned_word cia,
  1721. os_emul_data *emul_data)
  1722. {
  1723. emul_do_system_call(emul_data,
  1724. emul_data->syscalls,
  1725. cpu_registers(processor)->gpr[0],
  1726. 3, /*r3 contains arg0*/
  1727. processor,
  1728. cia);
  1729. }
  1730. const os_emul emul_solaris = {
  1731. "solaris",
  1732. emul_solaris_create,
  1733. emul_solaris_init,
  1734. emul_solaris_system_call,
  1735. 0, /*instruction_call*/
  1736. 0 /*data*/
  1737. };
  1738. /* EMULATION
  1739. Linux - Emulation of user programs for Linux/PPC
  1740. DESCRIPTION
  1741. */
  1742. /* Linux specific implementation */
  1743. typedef uint32_t linux_dev_t;
  1744. typedef uint32_t linux_ino_t;
  1745. typedef uint32_t linux_mode_t;
  1746. typedef uint16_t linux_nlink_t;
  1747. typedef int32_t linux_off_t;
  1748. typedef int32_t linux_pid_t;
  1749. typedef uint32_t linux_uid_t;
  1750. typedef uint32_t linux_gid_t;
  1751. typedef uint32_t linux_size_t;
  1752. typedef int32_t linux_ssize_t;
  1753. typedef int32_t linux_ptrdiff_t;
  1754. typedef int32_t linux_time_t;
  1755. typedef int32_t linux_clock_t;
  1756. typedef int32_t linux_daddr_t;
  1757. #ifdef HAVE_SYS_STAT_H
  1758. /* For the PowerPC, don't both with the 'old' stat structure, since there
  1759. should be no extant binaries with that structure. */
  1760. struct linux_stat {
  1761. linux_dev_t st_dev;
  1762. linux_ino_t st_ino;
  1763. linux_mode_t st_mode;
  1764. linux_nlink_t st_nlink;
  1765. linux_uid_t st_uid;
  1766. linux_gid_t st_gid;
  1767. linux_dev_t st_rdev;
  1768. linux_off_t st_size;
  1769. uint32_t st_blksize;
  1770. uint32_t st_blocks;
  1771. uint32_t st_atimx; /* don't use st_{a,c,m}time, that might a macro */
  1772. uint32_t __unused1; /* defined by the host's stat.h */
  1773. uint32_t st_mtimx;
  1774. uint32_t __unused2;
  1775. uint32_t st_ctimx;
  1776. uint32_t __unused3;
  1777. uint32_t __unused4;
  1778. uint32_t __unused5;
  1779. };
  1780. /* Convert from host stat structure to solaris stat structure */
  1781. STATIC_INLINE_EMUL_UNIX void
  1782. convert_to_linux_stat(unsigned_word addr,
  1783. struct stat *host,
  1784. cpu *processor,
  1785. unsigned_word cia)
  1786. {
  1787. struct linux_stat target;
  1788. target.st_dev = H2T_4(host->st_dev);
  1789. target.st_ino = H2T_4(host->st_ino);
  1790. target.st_mode = H2T_4(host->st_mode);
  1791. target.st_nlink = H2T_2(host->st_nlink);
  1792. target.st_uid = H2T_4(host->st_uid);
  1793. target.st_gid = H2T_4(host->st_gid);
  1794. target.st_size = H2T_4(host->st_size);
  1795. #ifdef HAVE_ST_RDEV
  1796. target.st_rdev = H2T_4(host->st_rdev);
  1797. #else
  1798. target.st_rdev = 0;
  1799. #endif
  1800. #ifdef HAVE_ST_BLKSIZE
  1801. target.st_blksize = H2T_4(host->st_blksize);
  1802. #else
  1803. target.st_blksize = 0;
  1804. #endif
  1805. #ifdef HAVE_ST_BLOCKS
  1806. target.st_blocks = H2T_4(host->st_blocks);
  1807. #else
  1808. target.st_blocks = 0;
  1809. #endif
  1810. target.st_atimx = H2T_4(host->st_atime);
  1811. target.st_ctimx = H2T_4(host->st_ctime);
  1812. target.st_mtimx = H2T_4(host->st_mtime);
  1813. target.__unused1 = 0;
  1814. target.__unused2 = 0;
  1815. target.__unused3 = 0;
  1816. target.__unused4 = 0;
  1817. target.__unused5 = 0;
  1818. emul_write_buffer(&target, addr, sizeof(target), processor, cia);
  1819. }
  1820. #endif /* HAVE_SYS_STAT_H */
  1821. #ifndef HAVE_STAT
  1822. #define do_linux_stat 0
  1823. #else
  1824. static void
  1825. do_linux_stat(os_emul_data *emul,
  1826. unsigned call,
  1827. const int arg0,
  1828. cpu *processor,
  1829. unsigned_word cia)
  1830. {
  1831. unsigned_word path_addr = cpu_registers(processor)->gpr[arg0];
  1832. unsigned_word stat_pkt = cpu_registers(processor)->gpr[arg0+1];
  1833. char path_buf[PATH_MAX];
  1834. struct stat buf;
  1835. char *path = emul_read_string(path_buf, path_addr, PATH_MAX, processor, cia);
  1836. int status;
  1837. if (WITH_TRACE && ppc_trace[trace_os_emul])
  1838. printf_filtered ("0x%lx [%s], 0x%lx", (long)path_addr, path, (long)stat_pkt);
  1839. status = stat (path, &buf);
  1840. if (status == 0)
  1841. convert_to_linux_stat (stat_pkt, &buf, processor, cia);
  1842. emul_write_status(processor, status, errno);
  1843. }
  1844. #endif
  1845. #ifndef HAVE_LSTAT
  1846. #define do_linux_lstat 0
  1847. #else
  1848. static void
  1849. do_linux_lstat(os_emul_data *emul,
  1850. unsigned call,
  1851. const int arg0,
  1852. cpu *processor,
  1853. unsigned_word cia)
  1854. {
  1855. unsigned_word path_addr = cpu_registers(processor)->gpr[arg0];
  1856. unsigned_word stat_pkt = cpu_registers(processor)->gpr[arg0+1];
  1857. char path_buf[PATH_MAX];
  1858. struct stat buf;
  1859. char *path = emul_read_string(path_buf, path_addr, PATH_MAX, processor, cia);
  1860. int status;
  1861. if (WITH_TRACE && ppc_trace[trace_os_emul])
  1862. printf_filtered ("0x%lx [%s], 0x%lx", (long)path_addr, path, (long)stat_pkt);
  1863. status = lstat (path, &buf);
  1864. if (status == 0)
  1865. convert_to_linux_stat (stat_pkt, &buf, processor, cia);
  1866. emul_write_status(processor, status, errno);
  1867. }
  1868. #endif
  1869. #ifndef HAVE_FSTAT
  1870. #define do_linux_fstat 0
  1871. #else
  1872. static void
  1873. do_linux_fstat(os_emul_data *emul,
  1874. unsigned call,
  1875. const int arg0,
  1876. cpu *processor,
  1877. unsigned_word cia)
  1878. {
  1879. int fildes = (int)cpu_registers(processor)->gpr[arg0];
  1880. unsigned_word stat_pkt = cpu_registers(processor)->gpr[arg0+1];
  1881. struct stat buf;
  1882. int status;
  1883. if (WITH_TRACE && ppc_trace[trace_os_emul])
  1884. printf_filtered ("%d, 0x%lx", fildes, (long)stat_pkt);
  1885. status = fdbad (fildes);
  1886. if (status == 0)
  1887. status = fstat (fildes, &buf);
  1888. if (status == 0)
  1889. convert_to_linux_stat (stat_pkt, &buf, processor, cia);
  1890. emul_write_status(processor, status, errno);
  1891. }
  1892. #endif
  1893. #if defined(HAVE_TERMIO_STRUCTURE) || defined(HAVE_TERMIOS_STRUCTURE)
  1894. #define LINUX_NCC 10
  1895. #define LINUX_NCCS 19
  1896. #define LINUX_VINTR 0
  1897. #define LINUX_VQUIT 1
  1898. #define LINUX_VERASE 2
  1899. #define LINUX_VKILL 3
  1900. #define LINUX_VEOF 4
  1901. #define LINUX_VMIN 5
  1902. #define LINUX_VEOL 6
  1903. #define LINUX_VTIME 7
  1904. #define LINUX_VEOL2 8
  1905. #define LINUX_VSWTC 9
  1906. #define LINUX_VWERASE 10
  1907. #define LINUX_VREPRINT 11
  1908. #define LINUX_VSUSP 12
  1909. #define LINUX_VSTART 13
  1910. #define LINUX_VSTOP 14
  1911. #define LINUX_VLNEXT 15
  1912. #define LINUX_VDISCARD 16
  1913. #define LINUX_IOC_NRBITS 8
  1914. #define LINUX_IOC_TYPEBITS 8
  1915. #define LINUX_IOC_SIZEBITS 13
  1916. #define LINUX_IOC_DIRBITS 3
  1917. #define LINUX_IOC_NRMASK ((1 << LINUX_IOC_NRBITS)-1)
  1918. #define LINUX_IOC_TYPEMASK ((1 << LINUX_IOC_TYPEBITS)-1)
  1919. #define LINUX_IOC_SIZEMASK ((1 << LINUX_IOC_SIZEBITS)-1)
  1920. #define LINUX_IOC_DIRMASK ((1 << LINUX_IOC_DIRBITS)-1)
  1921. #define LINUX_IOC_NRSHIFT 0
  1922. #define LINUX_IOC_TYPESHIFT (LINUX_IOC_NRSHIFT+LINUX_IOC_NRBITS)
  1923. #define LINUX_IOC_SIZESHIFT (LINUX_IOC_TYPESHIFT+LINUX_IOC_TYPEBITS)
  1924. #define LINUX_IOC_DIRSHIFT (LINUX_IOC_SIZESHIFT+LINUX_IOC_SIZEBITS)
  1925. /*
  1926. * Direction bits _IOC_NONE could be 0, but OSF/1 gives it a bit.
  1927. * And this turns out useful to catch old ioctl numbers in header
  1928. * files for us.
  1929. */
  1930. #define LINUX_IOC_NONE 1U
  1931. #define LINUX_IOC_READ 2U
  1932. #define LINUX_IOC_WRITE 4U
  1933. #define LINUX_IOC(dir,type,nr,size) \
  1934. (((dir) << LINUX_IOC_DIRSHIFT) | \
  1935. ((type) << LINUX_IOC_TYPESHIFT) | \
  1936. ((nr) << LINUX_IOC_NRSHIFT) | \
  1937. ((size) << LINUX_IOC_SIZESHIFT))
  1938. /* used to create numbers */
  1939. #define LINUX_IO(type,nr) LINUX_IOC(LINUX_IOC_NONE,(type),(nr),0)
  1940. #define LINUX_IOR(type,nr,size) LINUX_IOC(LINUX_IOC_READ,(type),(nr),sizeof(size))
  1941. #define LINUX_IOW(type,nr,size) LINUX_IOC(LINUX_IOC_WRITE,(type),(nr),sizeof(size))
  1942. #define LINUX_IOWR(type,nr,size) LINUX_IOC(LINUX_IOC_READ|LINUX_IOC_WRITE,(type),(nr),sizeof(size))
  1943. #endif
  1944. #if defined(HAVE_TERMIO_STRUCTURE) || defined(HAVE_TERMIOS_STRUCTURE)
  1945. /* Convert to/from host termio structure */
  1946. struct linux_termio {
  1947. uint16_t c_iflag; /* input modes */
  1948. uint16_t c_oflag; /* output modes */
  1949. uint16_t c_cflag; /* control modes */
  1950. uint16_t c_lflag; /* line discipline modes */
  1951. uint8_t c_line; /* line discipline */
  1952. uint8_t c_cc[LINUX_NCC]; /* control chars */
  1953. };
  1954. STATIC_INLINE_EMUL_UNIX void
  1955. convert_to_linux_termio(unsigned_word addr,
  1956. struct termio *host,
  1957. cpu *processor,
  1958. unsigned_word cia)
  1959. {
  1960. struct linux_termio target;
  1961. int i;
  1962. target.c_iflag = H2T_2 (host->c_iflag);
  1963. target.c_oflag = H2T_2 (host->c_oflag);
  1964. target.c_cflag = H2T_2 (host->c_cflag);
  1965. target.c_lflag = H2T_2 (host->c_lflag);
  1966. #if defined(HAVE_TERMIO_CLINE) || defined(HAVE_TERMIOS_CLINE)
  1967. target.c_line = host->c_line;
  1968. #else
  1969. target.c_line = 0;
  1970. #endif
  1971. for (i = 0; i < LINUX_NCC; i++)
  1972. target.c_cc[i] = 0;
  1973. #ifdef VINTR
  1974. target.c_cc[LINUX_VINTR] = host->c_cc[VINTR];
  1975. #endif
  1976. #ifdef VQUIT
  1977. target.c_cc[LINUX_VQUIT] = host->c_cc[VQUIT];
  1978. #endif
  1979. #ifdef VERASE
  1980. target.c_cc[LINUX_VERASE] = host->c_cc[VERASE];
  1981. #endif
  1982. #ifdef VKILL
  1983. target.c_cc[LINUX_VKILL] = host->c_cc[VKILL];
  1984. #endif
  1985. #ifdef VEOF
  1986. target.c_cc[LINUX_VEOF] = host->c_cc[VEOF];
  1987. #endif
  1988. #ifdef VMIN
  1989. target.c_cc[LINUX_VMIN] = host->c_cc[VMIN];
  1990. #endif
  1991. #ifdef VEOL
  1992. target.c_cc[LINUX_VEOL] = host->c_cc[VEOL];
  1993. #endif
  1994. #ifdef VTIME
  1995. target.c_cc[LINUX_VTIME] = host->c_cc[VTIME];
  1996. #endif
  1997. #ifdef VEOL2
  1998. target.c_cc[LINUX_VEOL2] = host->c_cc[VEOL2];
  1999. #endif
  2000. #ifdef VSWTC
  2001. target.c_cc[LINUX_VSWTC] = host->c_cc[VSWTC];
  2002. #endif
  2003. #ifdef VSWTCH
  2004. target.c_cc[LINUX_VSWTC] = host->c_cc[VSWTCH];
  2005. #endif
  2006. emul_write_buffer(&target, addr, sizeof(target), processor, cia);
  2007. }
  2008. #endif /* HAVE_TERMIO_STRUCTURE */
  2009. #ifdef HAVE_TERMIOS_STRUCTURE
  2010. /* Convert to/from host termios structure */
  2011. typedef uint32_t linux_tcflag_t;
  2012. typedef uint8_t linux_cc_t;
  2013. typedef uint32_t linux_speed_t;
  2014. struct linux_termios {
  2015. linux_tcflag_t c_iflag;
  2016. linux_tcflag_t c_oflag;
  2017. linux_tcflag_t c_cflag;
  2018. linux_tcflag_t c_lflag;
  2019. linux_cc_t c_cc[LINUX_NCCS];
  2020. linux_cc_t c_line;
  2021. int32_t c_ispeed;
  2022. int32_t c_ospeed;
  2023. };
  2024. STATIC_INLINE_EMUL_UNIX void
  2025. convert_to_linux_termios(unsigned_word addr,
  2026. struct termios *host,
  2027. cpu *processor,
  2028. unsigned_word cia)
  2029. {
  2030. struct linux_termios target;
  2031. int i;
  2032. target.c_iflag = H2T_4 (host->c_iflag);
  2033. target.c_oflag = H2T_4 (host->c_oflag);
  2034. target.c_cflag = H2T_4 (host->c_cflag);
  2035. target.c_lflag = H2T_4 (host->c_lflag);
  2036. for (i = 0; i < LINUX_NCCS; i++)
  2037. target.c_cc[i] = 0;
  2038. #ifdef VINTR
  2039. target.c_cc[LINUX_VINTR] = host->c_cc[VINTR];
  2040. #endif
  2041. #ifdef VQUIT
  2042. target.c_cc[LINUX_VQUIT] = host->c_cc[VQUIT];
  2043. #endif
  2044. #ifdef VERASE
  2045. target.c_cc[LINUX_VERASE] = host->c_cc[VERASE];
  2046. #endif
  2047. #ifdef VKILL
  2048. target.c_cc[LINUX_VKILL] = host->c_cc[VKILL];
  2049. #endif
  2050. #ifdef VEOF
  2051. target.c_cc[LINUX_VEOF] = host->c_cc[VEOF];
  2052. #endif
  2053. #ifdef VEOL
  2054. target.c_cc[LINUX_VEOL] = host->c_cc[VEOL];
  2055. #endif
  2056. #ifdef VEOL2
  2057. target.c_cc[LINUX_VEOL2] = host->c_cc[VEOL2];
  2058. #endif
  2059. #ifdef VSWTCH
  2060. target.c_cc[LINUX_VSWTC] = host->c_cc[VSWTCH];
  2061. #endif
  2062. #ifdef HAVE_TERMIOS_CLINE
  2063. target.c_line = host->c_line;
  2064. #else
  2065. target.c_line = 0;
  2066. #endif
  2067. #ifdef HAVE_CFGETISPEED
  2068. target.c_ispeed = cfgetispeed (host);
  2069. #else
  2070. target.c_ispeed = 0;
  2071. #endif
  2072. #ifdef HAVE_CFGETOSPEED
  2073. target.c_ospeed = cfgetospeed (host);
  2074. #else
  2075. target.c_ospeed = 0;
  2076. #endif
  2077. emul_write_buffer(&target, addr, sizeof(target), processor, cia);
  2078. }
  2079. #endif /* HAVE_TERMIOS_STRUCTURE */
  2080. #ifndef HAVE_IOCTL
  2081. #define do_linux_ioctl 0
  2082. #else
  2083. static void
  2084. do_linux_ioctl(os_emul_data *emul,
  2085. unsigned call,
  2086. const int arg0,
  2087. cpu *processor,
  2088. unsigned_word cia)
  2089. {
  2090. int fildes = cpu_registers(processor)->gpr[arg0];
  2091. unsigned request = cpu_registers(processor)->gpr[arg0+1];
  2092. unsigned_word argp_addr = cpu_registers(processor)->gpr[arg0+2];
  2093. int status = 0;
  2094. const char *name = "<unknown>";
  2095. #ifdef HAVE_TERMIOS_STRUCTURE
  2096. struct termios host_termio;
  2097. #else
  2098. #ifdef HAVE_TERMIO_STRUCTURE
  2099. struct termio host_termio;
  2100. #endif
  2101. #endif
  2102. status = fdbad (fildes);
  2103. if (status != 0)
  2104. goto done;
  2105. switch (request)
  2106. {
  2107. case 0: /* make sure we have at least one case */
  2108. default:
  2109. status = -1;
  2110. errno = EINVAL;
  2111. break;
  2112. #if defined(HAVE_TERMIO_STRUCTURE) || defined(HAVE_TERMIOS_STRUCTURE)
  2113. #if defined(TCGETA) || defined(TCGETS) || defined(HAVE_TCGETATTR)
  2114. case LINUX_IOR('t', 23, struct linux_termio): /* TCGETA */
  2115. name = "TCGETA";
  2116. #ifdef HAVE_TCGETATTR
  2117. status = tcgetattr(fildes, &host_termio);
  2118. #elif defined(TCGETS)
  2119. status = ioctl (fildes, TCGETS, &host_termio);
  2120. #else
  2121. status = ioctl (fildes, TCGETA, &host_termio);
  2122. #endif
  2123. if (status == 0)
  2124. convert_to_linux_termio (argp_addr, &host_termio, processor, cia);
  2125. break;
  2126. #endif /* TCGETA */
  2127. #endif /* HAVE_TERMIO_STRUCTURE */
  2128. #ifdef HAVE_TERMIOS_STRUCTURE
  2129. #if defined(TCGETS) || defined(HAVE_TCGETATTR)
  2130. case LINUX_IOR('t', 19, struct linux_termios): /* TCGETS */
  2131. name = "TCGETS";
  2132. #ifdef HAVE_TCGETATTR
  2133. status = tcgetattr(fildes, &host_termio);
  2134. #else
  2135. status = ioctl (fildes, TCGETS, &host_termio);
  2136. #endif
  2137. if (status == 0)
  2138. convert_to_linux_termios (argp_addr, &host_termio, processor, cia);
  2139. break;
  2140. #endif /* TCGETS */
  2141. #endif /* HAVE_TERMIOS_STRUCTURE */
  2142. }
  2143. done:
  2144. emul_write_status(processor, status, errno);
  2145. if (WITH_TRACE && ppc_trace[trace_os_emul])
  2146. printf_filtered ("%d, 0x%x [%s], 0x%lx", fildes, request, name, (long)argp_addr);
  2147. }
  2148. #endif /* HAVE_IOCTL */
  2149. static emul_syscall_descriptor linux_descriptors[] = {
  2150. /* 0 */ { 0, "setup" },
  2151. /* 1 */ { do_unix_exit, "exit" },
  2152. /* 2 */ { 0, "fork" },
  2153. /* 3 */ { do_unix_read, "read" },
  2154. /* 4 */ { do_unix_write, "write" },
  2155. /* 5 */ { do_unix_open, "open" },
  2156. /* 6 */ { do_unix_close, "close" },
  2157. /* 7 */ { 0, "waitpid" },
  2158. /* 8 */ { 0, "creat" },
  2159. /* 9 */ { do_unix_link, "link" },
  2160. /* 10 */ { do_unix_unlink, "unlink" },
  2161. /* 11 */ { 0, "execve" },
  2162. /* 12 */ { do_unix_chdir, "chdir" },
  2163. /* 13 */ { do_unix_time, "time" },
  2164. /* 14 */ { 0, "mknod" },
  2165. /* 15 */ { 0, "chmod" },
  2166. /* 16 */ { 0, "chown" },
  2167. /* 17 */ { 0, "break" },
  2168. /* 18 */ { 0, "stat" },
  2169. /* 19 */ { do_unix_lseek, "lseek" },
  2170. /* 20 */ { do_unix_getpid, "getpid" },
  2171. /* 21 */ { 0, "mount" },
  2172. /* 22 */ { 0, "umount" },
  2173. /* 23 */ { 0, "setuid" },
  2174. /* 24 */ { do_unix_getuid, "getuid" },
  2175. /* 25 */ { 0, "stime" },
  2176. /* 26 */ { 0, "ptrace" },
  2177. /* 27 */ { 0, "alarm" },
  2178. /* 28 */ { 0, "fstat" },
  2179. /* 29 */ { 0, "pause" },
  2180. /* 30 */ { 0, "utime" },
  2181. /* 31 */ { 0, "stty" },
  2182. /* 32 */ { 0, "gtty" },
  2183. /* 33 */ { do_unix_access, "access" },
  2184. /* 34 */ { 0, "nice" },
  2185. /* 35 */ { 0, "ftime" },
  2186. /* 36 */ { 0, "sync" },
  2187. /* 37 */ { 0, "kill" },
  2188. /* 38 */ { 0, "rename" },
  2189. /* 39 */ { do_unix_mkdir, "mkdir" },
  2190. /* 40 */ { do_unix_rmdir, "rmdir" },
  2191. /* 41 */ { do_unix_dup, "dup" },
  2192. /* 42 */ { 0, "pipe" },
  2193. /* 43 */ { 0, "times" },
  2194. /* 44 */ { 0, "prof" },
  2195. /* 45 */ { do_unix_break, "brk" },
  2196. /* 46 */ { 0, "setgid" },
  2197. /* 47 */ { do_unix_getgid, "getgid" },
  2198. /* 48 */ { 0, "signal" },
  2199. /* 49 */ { do_unix_geteuid, "geteuid" },
  2200. /* 50 */ { do_unix_getegid, "getegid" },
  2201. /* 51 */ { 0, "acct" },
  2202. /* 52 */ { 0, "phys" },
  2203. /* 53 */ { 0, "lock" },
  2204. /* 54 */ { do_linux_ioctl, "ioctl" },
  2205. /* 55 */ { 0, "fcntl" },
  2206. /* 56 */ { 0, "mpx" },
  2207. /* 57 */ { 0, "setpgid" },
  2208. /* 58 */ { 0, "ulimit" },
  2209. /* 59 */ { 0, "olduname" },
  2210. /* 60 */ { do_unix_umask, "umask" },
  2211. /* 61 */ { 0, "chroot" },
  2212. /* 62 */ { 0, "ustat" },
  2213. /* 63 */ { do_unix_dup2, "dup2" },
  2214. /* 64 */ { do_unix_getppid, "getppid" },
  2215. /* 65 */ { 0, "getpgrp" },
  2216. /* 66 */ { 0, "setsid" },
  2217. /* 67 */ { 0, "sigaction" },
  2218. /* 68 */ { 0, "sgetmask" },
  2219. /* 69 */ { 0, "ssetmask" },
  2220. /* 70 */ { 0, "setreuid" },
  2221. /* 71 */ { 0, "setregid" },
  2222. /* 72 */ { 0, "sigsuspend" },
  2223. /* 73 */ { 0, "sigpending" },
  2224. /* 74 */ { 0, "sethostname" },
  2225. /* 75 */ { 0, "setrlimit" },
  2226. /* 76 */ { 0, "getrlimit" },
  2227. /* 77 */ { do_unix_getrusage, "getrusage" },
  2228. /* 78 */ { do_unix_gettimeofday, "gettimeofday" },
  2229. /* 79 */ { 0, "settimeofday" },
  2230. /* 80 */ { 0, "getgroups" },
  2231. /* 81 */ { 0, "setgroups" },
  2232. /* 82 */ { 0, "select" },
  2233. /* 83 */ { do_unix_symlink, "symlink" },
  2234. /* 84 */ { 0, "lstat" },
  2235. /* 85 */ { 0, "readlink" },
  2236. /* 86 */ { 0, "uselib" },
  2237. /* 87 */ { 0, "swapon" },
  2238. /* 88 */ { 0, "reboot" },
  2239. /* 89 */ { 0, "readdir" },
  2240. /* 90 */ { 0, "mmap" },
  2241. /* 91 */ { 0, "munmap" },
  2242. /* 92 */ { 0, "truncate" },
  2243. /* 93 */ { 0, "ftruncate" },
  2244. /* 94 */ { 0, "fchmod" },
  2245. /* 95 */ { 0, "fchown" },
  2246. /* 96 */ { 0, "getpriority" },
  2247. /* 97 */ { 0, "setpriority" },
  2248. /* 98 */ { 0, "profil" },
  2249. /* 99 */ { 0, "statfs" },
  2250. /* 100 */ { 0, "fstatfs" },
  2251. /* 101 */ { 0, "ioperm" },
  2252. /* 102 */ { 0, "socketcall" },
  2253. /* 103 */ { 0, "syslog" },
  2254. /* 104 */ { 0, "setitimer" },
  2255. /* 105 */ { 0, "getitimer" },
  2256. /* 106 */ { do_linux_stat, "newstat" },
  2257. /* 107 */ { do_linux_lstat, "newlstat" },
  2258. /* 108 */ { do_linux_fstat, "newfstat" },
  2259. /* 109 */ { 0, "uname" },
  2260. /* 110 */ { 0, "iopl" },
  2261. /* 111 */ { 0, "vhangup" },
  2262. /* 112 */ { 0, "idle" },
  2263. /* 113 */ { 0, "vm86" },
  2264. /* 114 */ { 0, "wait4" },
  2265. /* 115 */ { 0, "swapoff" },
  2266. /* 116 */ { 0, "sysinfo" },
  2267. /* 117 */ { 0, "ipc" },
  2268. /* 118 */ { 0, "fsync" },
  2269. /* 119 */ { 0, "sigreturn" },
  2270. /* 120 */ { 0, "clone" },
  2271. /* 121 */ { 0, "setdomainname" },
  2272. /* 122 */ { 0, "newuname" },
  2273. /* 123 */ { 0, "modify_ldt" },
  2274. /* 124 */ { 0, "adjtimex" },
  2275. /* 125 */ { 0, "mprotect" },
  2276. /* 126 */ { 0, "sigprocmask" },
  2277. /* 127 */ { 0, "create_module" },
  2278. /* 128 */ { 0, "init_module" },
  2279. /* 129 */ { 0, "delete_module" },
  2280. /* 130 */ { 0, "get_kernel_syms" },
  2281. /* 131 */ { 0, "quotactl" },
  2282. /* 132 */ { 0, "getpgid" },
  2283. /* 133 */ { 0, "fchdir" },
  2284. /* 134 */ { 0, "bdflush" },
  2285. /* 135 */ { 0, "sysfs" },
  2286. /* 136 */ { 0, "personality" },
  2287. /* 137 */ { 0, "afs_syscall" },
  2288. /* 138 */ { 0, "setfsuid" },
  2289. /* 139 */ { 0, "setfsgid" },
  2290. /* 140 */ { 0, "llseek" },
  2291. /* 141 */ { 0, "getdents" },
  2292. /* 142 */ { 0, "newselect" },
  2293. /* 143 */ { 0, "flock" },
  2294. /* 144 */ { 0, "msync" },
  2295. /* 145 */ { 0, "readv" },
  2296. /* 146 */ { 0, "writev" },
  2297. /* 147 */ { 0, "getsid" },
  2298. /* 148 */ { 0, "fdatasync" },
  2299. /* 149 */ { 0, "sysctl" },
  2300. /* 150 */ { 0, "mlock" },
  2301. /* 151 */ { 0, "munlock" },
  2302. /* 152 */ { 0, "mlockall" },
  2303. /* 153 */ { 0, "munlockall" },
  2304. /* 154 */ { 0, "sched_setparam" },
  2305. /* 155 */ { 0, "sched_getparam" },
  2306. /* 156 */ { 0, "sched_setscheduler" },
  2307. /* 157 */ { 0, "sched_getscheduler" },
  2308. /* 158 */ { 0, "sched_yield" },
  2309. /* 159 */ { 0, "sched_get_priority_max" },
  2310. /* 160 */ { 0, "sched_get_priority_min" },
  2311. /* 161 */ { 0, "sched_rr_get_interval" },
  2312. };
  2313. static char *(linux_error_names[]) = {
  2314. /* 0 */ "ESUCCESS",
  2315. /* 1 */ "EPERM",
  2316. /* 2 */ "ENOENT",
  2317. /* 3 */ "ESRCH",
  2318. /* 4 */ "EINTR",
  2319. /* 5 */ "EIO",
  2320. /* 6 */ "ENXIO",
  2321. /* 7 */ "E2BIG",
  2322. /* 8 */ "ENOEXEC",
  2323. /* 9 */ "EBADF",
  2324. /* 10 */ "ECHILD",
  2325. /* 11 */ "EAGAIN",
  2326. /* 12 */ "ENOMEM",
  2327. /* 13 */ "EACCES",
  2328. /* 14 */ "EFAULT",
  2329. /* 15 */ "ENOTBLK",
  2330. /* 16 */ "EBUSY",
  2331. /* 17 */ "EEXIST",
  2332. /* 18 */ "EXDEV",
  2333. /* 19 */ "ENODEV",
  2334. /* 20 */ "ENOTDIR",
  2335. /* 21 */ "EISDIR",
  2336. /* 22 */ "EINVAL",
  2337. /* 23 */ "ENFILE",
  2338. /* 24 */ "EMFILE",
  2339. /* 25 */ "ENOTTY",
  2340. /* 26 */ "ETXTBSY",
  2341. /* 27 */ "EFBIG",
  2342. /* 28 */ "ENOSPC",
  2343. /* 29 */ "ESPIPE",
  2344. /* 30 */ "EROFS",
  2345. /* 31 */ "EMLINK",
  2346. /* 32 */ "EPIPE",
  2347. /* 33 */ "EDOM",
  2348. /* 34 */ "ERANGE",
  2349. /* 35 */ "EDEADLK",
  2350. /* 36 */ "ENAMETOOLONG",
  2351. /* 37 */ "ENOLCK",
  2352. /* 38 */ "ENOSYS",
  2353. /* 39 */ "ENOTEMPTY",
  2354. /* 40 */ "ELOOP",
  2355. /* 41 */ 0,
  2356. /* 42 */ "ENOMSG",
  2357. /* 43 */ "EIDRM",
  2358. /* 44 */ "ECHRNG",
  2359. /* 45 */ "EL2NSYNC",
  2360. /* 46 */ "EL3HLT",
  2361. /* 47 */ "EL3RST",
  2362. /* 48 */ "ELNRNG",
  2363. /* 49 */ "EUNATCH",
  2364. /* 50 */ "ENOCSI",
  2365. /* 51 */ "EL2HLT",
  2366. /* 52 */ "EBADE",
  2367. /* 53 */ "EBADR",
  2368. /* 54 */ "EXFULL",
  2369. /* 55 */ "ENOANO",
  2370. /* 56 */ "EBADRQC",
  2371. /* 57 */ "EBADSLT",
  2372. /* 58 */ "EDEADLOCK",
  2373. /* 59 */ "EBFONT",
  2374. /* 60 */ "ENOSTR",
  2375. /* 61 */ "ENODATA",
  2376. /* 62 */ "ETIME",
  2377. /* 63 */ "ENOSR",
  2378. /* 64 */ "ENONET",
  2379. /* 65 */ "ENOPKG",
  2380. /* 66 */ "EREMOTE",
  2381. /* 67 */ "ENOLINK",
  2382. /* 68 */ "EADV",
  2383. /* 69 */ "ESRMNT",
  2384. /* 70 */ "ECOMM",
  2385. /* 71 */ "EPROTO",
  2386. /* 72 */ "EMULTIHOP",
  2387. /* 73 */ "EDOTDOT",
  2388. /* 74 */ "EBADMSG",
  2389. /* 75 */ "EOVERFLOW",
  2390. /* 76 */ "ENOTUNIQ",
  2391. /* 77 */ "EBADFD",
  2392. /* 78 */ "EREMCHG",
  2393. /* 79 */ "ELIBACC",
  2394. /* 80 */ "ELIBBAD",
  2395. /* 81 */ "ELIBSCN",
  2396. /* 82 */ "ELIBMAX",
  2397. /* 83 */ "ELIBEXEC",
  2398. /* 84 */ "EILSEQ",
  2399. /* 85 */ "ERESTART",
  2400. /* 86 */ "ESTRPIPE",
  2401. /* 87 */ "EUSERS",
  2402. /* 88 */ "ENOTSOCK",
  2403. /* 89 */ "EDESTADDRREQ",
  2404. /* 90 */ "EMSGSIZE",
  2405. /* 91 */ "EPROTOTYPE",
  2406. /* 92 */ "ENOPROTOOPT",
  2407. /* 93 */ "EPROTONOSUPPORT",
  2408. /* 94 */ "ESOCKTNOSUPPORT",
  2409. /* 95 */ "EOPNOTSUPP",
  2410. /* 96 */ "EPFNOSUPPORT",
  2411. /* 97 */ "EAFNOSUPPORT",
  2412. /* 98 */ "EADDRINUSE",
  2413. /* 99 */ "EADDRNOTAVAIL",
  2414. /* 100 */ "ENETDOWN",
  2415. /* 101 */ "ENETUNREACH",
  2416. /* 102 */ "ENETRESET",
  2417. /* 103 */ "ECONNABORTED",
  2418. /* 104 */ "ECONNRESET",
  2419. /* 105 */ "ENOBUFS",
  2420. /* 106 */ "EISCONN",
  2421. /* 107 */ "ENOTCONN",
  2422. /* 108 */ "ESHUTDOWN",
  2423. /* 109 */ "ETOOMANYREFS",
  2424. /* 110 */ "ETIMEDOUT",
  2425. /* 111 */ "ECONNREFUSED",
  2426. /* 112 */ "EHOSTDOWN",
  2427. /* 113 */ "EHOSTUNREACH",
  2428. /* 114 */ "EALREADY",
  2429. /* 115 */ "EINPROGRESS",
  2430. /* 116 */ "ESTALE",
  2431. /* 117 */ "EUCLEAN",
  2432. /* 118 */ "ENOTNAM",
  2433. /* 119 */ "ENAVAIL",
  2434. /* 120 */ "EISNAM",
  2435. /* 121 */ "EREMOTEIO",
  2436. /* 122 */ "EDQUOT",
  2437. };
  2438. static char *(linux_signal_names[]) = {
  2439. /* 0 */ 0,
  2440. /* 1 */ "SIGHUP",
  2441. /* 2 */ "SIGINT",
  2442. /* 3 */ "SIGQUIT",
  2443. /* 4 */ "SIGILL",
  2444. /* 5 */ "SIGTRAP",
  2445. /* 6 */ "SIGABRT",
  2446. /* 6 */ "SIGIOT",
  2447. /* 7 */ "SIGBUS",
  2448. /* 8 */ "SIGFPE",
  2449. /* 9 */ "SIGKILL",
  2450. /* 10 */ "SIGUSR1",
  2451. /* 11 */ "SIGSEGV",
  2452. /* 12 */ "SIGUSR2",
  2453. /* 13 */ "SIGPIPE",
  2454. /* 14 */ "SIGALRM",
  2455. /* 15 */ "SIGTERM",
  2456. /* 16 */ "SIGSTKFLT",
  2457. /* 17 */ "SIGCHLD",
  2458. /* 18 */ "SIGCONT",
  2459. /* 19 */ "SIGSTOP",
  2460. /* 20 */ "SIGTSTP",
  2461. /* 21 */ "SIGTTIN",
  2462. /* 22 */ "SIGTTOU",
  2463. /* 23 */ "SIGURG",
  2464. /* 24 */ "SIGXCPU",
  2465. /* 25 */ "SIGXFSZ",
  2466. /* 26 */ "SIGVTALRM",
  2467. /* 27 */ "SIGPROF",
  2468. /* 28 */ "SIGWINCH",
  2469. /* 29 */ "SIGIO",
  2470. /* 30 */ "SIGPWR",
  2471. /* 31 */ "SIGUNUSED",
  2472. };
  2473. static emul_syscall emul_linux_syscalls = {
  2474. linux_descriptors,
  2475. ARRAY_SIZE (linux_descriptors),
  2476. linux_error_names,
  2477. ARRAY_SIZE (linux_error_names),
  2478. linux_signal_names,
  2479. ARRAY_SIZE (linux_signal_names),
  2480. };
  2481. /* Linux's os_emul interface, most are just passed on to the generic
  2482. syscall stuff */
  2483. static os_emul_data *
  2484. emul_linux_create(device *root,
  2485. bfd *image,
  2486. const char *name)
  2487. {
  2488. /* check that this emulation is really for us */
  2489. if (name != NULL && strcmp(name, "linux") != 0)
  2490. return NULL;
  2491. if (image == NULL)
  2492. return NULL;
  2493. return emul_unix_create(root, image, "linux", &emul_linux_syscalls);
  2494. }
  2495. static void
  2496. emul_linux_init(os_emul_data *emul_data,
  2497. int nr_cpus)
  2498. {
  2499. fd_closed[0] = 0;
  2500. fd_closed[1] = 0;
  2501. fd_closed[2] = 0;
  2502. }
  2503. static void
  2504. emul_linux_system_call(cpu *processor,
  2505. unsigned_word cia,
  2506. os_emul_data *emul_data)
  2507. {
  2508. emul_do_system_call(emul_data,
  2509. emul_data->syscalls,
  2510. cpu_registers(processor)->gpr[0],
  2511. 3, /*r3 contains arg0*/
  2512. processor,
  2513. cia);
  2514. }
  2515. const os_emul emul_linux = {
  2516. "linux",
  2517. emul_linux_create,
  2518. emul_linux_init,
  2519. emul_linux_system_call,
  2520. 0, /*instruction_call*/
  2521. 0 /*data*/
  2522. };
  2523. #endif /* _EMUL_UNIX_C_ */