systrace.c 40 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813
  1. /* $OpenBSD: systrace.c,v 1.75 2015/03/14 03:38:46 jsg Exp $ */
  2. /*
  3. * Copyright 2002 Niels Provos <provos@citi.umich.edu>
  4. * All rights reserved.
  5. *
  6. * Redistribution and use in source and binary forms, with or without
  7. * modification, are permitted provided that the following conditions
  8. * are met:
  9. * 1. Redistributions of source code must retain the above copyright
  10. * notice, this list of conditions and the following disclaimer.
  11. * 2. Redistributions in binary form must reproduce the above copyright
  12. * notice, this list of conditions and the following disclaimer in the
  13. * documentation and/or other materials provided with the distribution.
  14. * 3. All advertising materials mentioning features or use of this software
  15. * must display the following acknowledgement:
  16. * This product includes software developed by Niels Provos.
  17. * 4. The name of the author may not be used to endorse or promote products
  18. * derived from this software without specific prior written permission.
  19. *
  20. * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
  21. * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
  22. * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
  23. * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
  24. * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
  25. * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
  26. * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
  27. * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  28. * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  29. * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  30. */
  31. #include <sys/param.h>
  32. #include <sys/systm.h>
  33. #include <sys/tree.h>
  34. #include <sys/malloc.h>
  35. #include <sys/syscall.h>
  36. #include <sys/vnode.h>
  37. #include <sys/errno.h>
  38. #include <sys/device.h>
  39. #include <sys/proc.h>
  40. #include <sys/file.h>
  41. #include <sys/filedesc.h>
  42. #include <sys/filio.h>
  43. #include <sys/signalvar.h>
  44. #include <sys/rwlock.h>
  45. #include <sys/pool.h>
  46. #include <sys/mount.h>
  47. #include <sys/namei.h>
  48. #include <sys/poll.h>
  49. #include <sys/ptrace.h>
  50. #include <compat/common/compat_util.h>
  51. #include <dev/systrace.h>
  52. void systraceattach(int);
  53. int systraceopen(dev_t, int, int, struct proc *);
  54. int systraceclose(dev_t, int, int, struct proc *);
  55. int systraceioctl(dev_t, u_long, caddr_t, int, struct proc *);
  56. int systracef_read(struct file *, off_t *, struct uio *, struct ucred *);
  57. int systracef_write(struct file *, off_t *, struct uio *, struct ucred *);
  58. int systracef_ioctl(struct file *, u_long, caddr_t, struct proc *p);
  59. int systracef_poll(struct file *, int, struct proc *);
  60. int systracef_kqfilter(struct file *, struct knote *);
  61. int systracef_stat(struct file *, struct stat *, struct proc *);
  62. int systracef_close(struct file *, struct proc *);
  63. struct str_policy {
  64. TAILQ_ENTRY(str_policy) next;
  65. int nr;
  66. struct emul *emul; /* Is only valid for this emulation */
  67. int refcount;
  68. int nsysent;
  69. u_char *sysent;
  70. };
  71. struct str_inject {
  72. caddr_t kaddr;
  73. caddr_t uaddr;
  74. size_t len;
  75. };
  76. #define STR_PROC_ONQUEUE 0x01
  77. #define STR_PROC_WAITANSWER 0x02
  78. #define STR_PROC_SYSCALLRES 0x04
  79. #define STR_PROC_REPORT 0x08 /* Report emulation */
  80. #define STR_PROC_NEEDSEQNR 0x10 /* Answer must quote seqnr */
  81. #define STR_PROC_SETEUID 0x20 /* Elevate privileges */
  82. #define STR_PROC_SETEGID 0x40
  83. struct str_process {
  84. TAILQ_ENTRY(str_process) next;
  85. TAILQ_ENTRY(str_process) msg_next;
  86. struct str_process *firstmsg;
  87. struct proc *proc;
  88. pid_t pid;
  89. struct fsystrace *parent;
  90. struct str_policy *policy;
  91. struct systrace_replace *replace;
  92. char *fname[SYSTR_MAXFNAME];
  93. size_t nfname;
  94. int flags;
  95. short answer;
  96. short error;
  97. u_int16_t seqnr; /* expected reply sequence number */
  98. uid_t seteuid;
  99. gid_t setegid;
  100. int isscript;
  101. char scriptname[MAXPATHLEN];
  102. struct str_message msg;
  103. caddr_t sg;
  104. struct str_inject injects[SYSTR_MAXINJECTS];
  105. int injectind;
  106. };
  107. struct rwlock systrace_lck;
  108. static __inline void
  109. systrace_lock(void)
  110. {
  111. rw_enter_write(&systrace_lck);
  112. }
  113. static __inline void
  114. systrace_unlock(void)
  115. {
  116. rw_exit_write(&systrace_lck);
  117. }
  118. /* Needs to be called with fst locked */
  119. int systrace_attach(struct fsystrace *, pid_t);
  120. int systrace_detach(struct str_process *);
  121. int systrace_answer(struct str_process *, struct systrace_answer *);
  122. int systrace_setscriptname(struct str_process *,
  123. struct systrace_scriptname *);
  124. int systrace_prepinject(struct str_process *, struct systrace_inject *);
  125. int systrace_inject(struct str_process *, int);
  126. int systrace_io(struct str_process *, struct systrace_io *);
  127. int systrace_policy(struct fsystrace *, struct systrace_policy *);
  128. int systrace_preprepl(struct str_process *, struct systrace_replace *);
  129. int systrace_replace(struct str_process *, size_t, register_t []);
  130. int systrace_getcwd(struct fsystrace *, struct str_process *, int);
  131. int systrace_restorecwd(struct fsystrace *, struct proc *);
  132. int systrace_fname(struct str_process *, caddr_t, size_t);
  133. void systrace_replacefree(struct str_process *);
  134. int systrace_processready(struct str_process *);
  135. struct proc *systrace_find(struct str_process *);
  136. struct str_process *systrace_findpid(struct fsystrace *fst, pid_t pid);
  137. void systrace_wakeup(struct fsystrace *);
  138. void systrace_closepolicy(struct fsystrace *, struct str_policy *);
  139. void systrace_insert_process(struct fsystrace *, struct proc *,
  140. struct str_process *);
  141. struct str_policy *systrace_newpolicy(struct fsystrace *, int);
  142. int systrace_msg_child(struct fsystrace *, struct str_process *, pid_t);
  143. int systrace_msg_policyfree(struct fsystrace *, struct str_policy *);
  144. int systrace_msg_ask(struct fsystrace *, struct str_process *,
  145. int, size_t, register_t []);
  146. int systrace_msg_result(struct fsystrace *, struct str_process *,
  147. int, int, size_t, register_t [], register_t []);
  148. int systrace_msg_emul(struct fsystrace *, struct str_process *);
  149. int systrace_msg_ugid(struct fsystrace *, struct str_process *);
  150. int systrace_make_msg(struct str_process *, int);
  151. static struct fileops systracefops = {
  152. systracef_read,
  153. systracef_write,
  154. systracef_ioctl,
  155. systracef_poll,
  156. systracef_kqfilter,
  157. systracef_stat,
  158. systracef_close
  159. };
  160. struct pool systr_proc_pl;
  161. struct pool systr_policy_pl;
  162. int systrace_debug = 0;
  163. #define DPRINTF(y) if (systrace_debug) printf y;
  164. /* ARGSUSED */
  165. int
  166. systracef_read(struct file *fp, off_t *poff, struct uio *uio,
  167. struct ucred *cred)
  168. {
  169. struct fsystrace *fst = (struct fsystrace *)fp->f_data;
  170. struct str_process *process;
  171. int error = 0;
  172. if (uio->uio_resid != sizeof(struct str_message))
  173. return (EINVAL);
  174. again:
  175. systrace_lock();
  176. rw_enter_write(&fst->lock);
  177. systrace_unlock();
  178. if ((process = TAILQ_FIRST(&fst->messages)) != NULL) {
  179. error = uiomove((caddr_t)&process->msg,
  180. sizeof(struct str_message), uio);
  181. if (!error) {
  182. TAILQ_REMOVE(&fst->messages, process, msg_next);
  183. CLR(process->flags, STR_PROC_ONQUEUE);
  184. if (SYSTR_MSG_NOPROCESS(process))
  185. pool_put(&systr_proc_pl, process);
  186. }
  187. } else if (TAILQ_FIRST(&fst->processes) == NULL) {
  188. /* EOF situation */
  189. ;
  190. } else {
  191. if (fp->f_flag & FNONBLOCK)
  192. error = EAGAIN;
  193. else {
  194. rw_exit_write(&fst->lock);
  195. error = tsleep(fst, PWAIT|PCATCH, "systrrd", 0);
  196. if (error)
  197. goto out;
  198. goto again;
  199. }
  200. }
  201. rw_exit_write(&fst->lock);
  202. out:
  203. return (error);
  204. }
  205. /* ARGSUSED */
  206. int
  207. systracef_write(struct file *fp, off_t *poff, struct uio *uio,
  208. struct ucred *cred)
  209. {
  210. return (EIO);
  211. }
  212. #define POLICY_VALID(x) ((x) == SYSTR_POLICY_PERMIT || \
  213. (x) == SYSTR_POLICY_ASK || \
  214. (x) == SYSTR_POLICY_NEVER || \
  215. (x) == SYSTR_POLICY_KILL)
  216. /* ARGSUSED */
  217. int
  218. systracef_ioctl(struct file *fp, u_long cmd, caddr_t data, struct proc *p)
  219. {
  220. int ret = 0;
  221. struct fsystrace *fst = (struct fsystrace *)fp->f_data;
  222. struct str_process *strp;
  223. pid_t pid = 0;
  224. int atfd = -1;
  225. switch (cmd) {
  226. case FIONBIO:
  227. case FIOASYNC:
  228. return (0);
  229. case STRIOCDETACH:
  230. case STRIOCREPORT:
  231. pid = *(pid_t *)data;
  232. if (!pid)
  233. ret = EINVAL;
  234. break;
  235. case STRIOCANSWER:
  236. pid = ((struct systrace_answer *)data)->stra_pid;
  237. if (!pid)
  238. ret = EINVAL;
  239. break;
  240. case STRIOCIO:
  241. pid = ((struct systrace_io *)data)->strio_pid;
  242. if (!pid)
  243. ret = EINVAL;
  244. break;
  245. case STRIOCSCRIPTNAME:
  246. pid = ((struct systrace_scriptname *)data)->sn_pid;
  247. if (!pid)
  248. ret = EINVAL;
  249. break;
  250. case STRIOCINJECT:
  251. pid = ((struct systrace_inject *)data)->stri_pid;
  252. if (!pid)
  253. ret = EINVAL;
  254. break;
  255. case STRIOCGETCWD: {
  256. struct systrace_getcwd *gd = (struct systrace_getcwd *)data;
  257. pid = gd->strgd_pid;
  258. if (!pid)
  259. ret = EINVAL;
  260. atfd = gd->strgd_atfd;
  261. break;
  262. }
  263. case STRIOCATTACH:
  264. case STRIOCRESCWD:
  265. case STRIOCPOLICY:
  266. break;
  267. case STRIOCREPLACE:
  268. pid = ((struct systrace_replace *)data)->strr_pid;
  269. if (!pid)
  270. ret = EINVAL;
  271. break;
  272. default:
  273. ret = ENOTTY;
  274. break;
  275. }
  276. if (ret)
  277. return (ret);
  278. systrace_lock();
  279. rw_enter_write(&fst->lock);
  280. systrace_unlock();
  281. if (pid) {
  282. strp = systrace_findpid(fst, pid);
  283. if (strp == NULL) {
  284. ret = ESRCH;
  285. goto unlock;
  286. }
  287. }
  288. switch (cmd) {
  289. case STRIOCATTACH:
  290. pid = *(pid_t *)data;
  291. if (!pid)
  292. ret = EINVAL;
  293. else
  294. ret = systrace_attach(fst, pid);
  295. DPRINTF(("%s: attach to %u: %d\n", __func__, pid, ret));
  296. break;
  297. case STRIOCDETACH:
  298. ret = systrace_detach(strp);
  299. break;
  300. case STRIOCREPORT:
  301. SET(strp->flags, STR_PROC_REPORT);
  302. break;
  303. case STRIOCANSWER:
  304. ret = systrace_answer(strp, (struct systrace_answer *)data);
  305. break;
  306. case STRIOCIO:
  307. ret = systrace_io(strp, (struct systrace_io *)data);
  308. break;
  309. case STRIOCSCRIPTNAME:
  310. ret = systrace_setscriptname(strp,
  311. (struct systrace_scriptname *)data);
  312. break;
  313. case STRIOCINJECT:
  314. ret = systrace_prepinject(strp, (struct systrace_inject *)data);
  315. break;
  316. case STRIOCPOLICY:
  317. ret = systrace_policy(fst, (struct systrace_policy *)data);
  318. break;
  319. case STRIOCREPLACE:
  320. ret = systrace_preprepl(strp, (struct systrace_replace *)data);
  321. break;
  322. case STRIOCRESCWD:
  323. ret = systrace_restorecwd(fst, p);
  324. break;
  325. case STRIOCGETCWD:
  326. ret = systrace_getcwd(fst, strp, atfd);
  327. break;
  328. default:
  329. ret = ENOTTY;
  330. break;
  331. }
  332. unlock:
  333. rw_exit_write(&fst->lock);
  334. return (ret);
  335. }
  336. /* ARGSUSED */
  337. int
  338. systracef_poll(struct file *fp, int events, struct proc *p)
  339. {
  340. struct fsystrace *fst = (struct fsystrace *)fp->f_data;
  341. int revents = 0;
  342. if ((events & (POLLIN | POLLRDNORM)) == 0)
  343. return (0);
  344. systrace_lock();
  345. rw_enter_write(&fst->lock);
  346. systrace_unlock();
  347. if (!TAILQ_EMPTY(&fst->messages))
  348. revents = events & (POLLIN | POLLRDNORM);
  349. else
  350. selrecord(p, &fst->si);
  351. rw_exit_write(&fst->lock);
  352. return (revents);
  353. }
  354. /* ARGSUSED */
  355. int
  356. systracef_kqfilter(struct file *fp, struct knote *kn)
  357. {
  358. return (1);
  359. }
  360. /* ARGSUSED */
  361. int
  362. systracef_stat(struct file *fp, struct stat *sb, struct proc *p)
  363. {
  364. return (EOPNOTSUPP);
  365. }
  366. /* ARGSUSED */
  367. int
  368. systracef_close(struct file *fp, struct proc *p)
  369. {
  370. struct fsystrace *fst = (struct fsystrace *)fp->f_data;
  371. struct str_process *strp;
  372. struct str_policy *strpol;
  373. systrace_lock();
  374. rw_enter_write(&fst->lock);
  375. systrace_unlock();
  376. /* Untrace all processes */
  377. for (strp = TAILQ_FIRST(&fst->processes); strp;
  378. strp = TAILQ_FIRST(&fst->processes)) {
  379. struct proc *q = strp->proc;
  380. systrace_detach(strp);
  381. psignal(q, SIGKILL);
  382. }
  383. /* Clean up fork and exit messages */
  384. for (strp = TAILQ_FIRST(&fst->messages); strp;
  385. strp = TAILQ_FIRST(&fst->messages)) {
  386. TAILQ_REMOVE(&fst->messages, strp, msg_next);
  387. pool_put(&systr_proc_pl, strp);
  388. }
  389. /* Clean up all policies */
  390. for (strpol = TAILQ_FIRST(&fst->policies); strpol;
  391. strpol = TAILQ_FIRST(&fst->policies))
  392. systrace_closepolicy(fst, strpol);
  393. /* Release vnodes */
  394. if (fst->fd_cdir)
  395. vrele(fst->fd_cdir);
  396. if (fst->fd_rdir)
  397. vrele(fst->fd_rdir);
  398. rw_exit_write(&fst->lock);
  399. free(fp->f_data, M_XDATA, 0);
  400. fp->f_data = NULL;
  401. return (0);
  402. }
  403. void
  404. systraceattach(int n)
  405. {
  406. pool_init(&systr_proc_pl, sizeof(struct str_process), 0, 0, 0,
  407. "strprocpl", NULL);
  408. pool_init(&systr_policy_pl, sizeof(struct str_policy), 0, 0, 0,
  409. "strpolpl", NULL);
  410. rw_init(&systrace_lck, "systrace");
  411. }
  412. int
  413. systraceopen(dev_t dev, int flag, int mode, struct proc *p)
  414. {
  415. return (0);
  416. }
  417. int
  418. systraceclose(dev_t dev, int flag, int mode, struct proc *p)
  419. {
  420. return (0);
  421. }
  422. int
  423. systraceioctl(dev_t dev, u_long cmd, caddr_t data, int flag, struct proc *p)
  424. {
  425. struct file *f;
  426. struct fsystrace *fst = NULL;
  427. int fd, error;
  428. switch (cmd) {
  429. case STRIOCCLONE:
  430. fst = (struct fsystrace *)malloc(sizeof(struct fsystrace),
  431. M_XDATA, M_WAITOK | M_ZERO);
  432. rw_init(&fst->lock, "systrace");
  433. TAILQ_INIT(&fst->processes);
  434. TAILQ_INIT(&fst->messages);
  435. TAILQ_INIT(&fst->policies);
  436. if (suser(p, 0) == 0)
  437. fst->issuser = 1;
  438. fst->p_ruid = p->p_ucred->cr_ruid;
  439. fst->p_rgid = p->p_ucred->cr_rgid;
  440. fdplock(p->p_fd);
  441. error = falloc(p, &f, &fd);
  442. fdpunlock(p->p_fd);
  443. if (error) {
  444. free(fst, M_XDATA, 0);
  445. return (error);
  446. }
  447. f->f_flag = FREAD | FWRITE;
  448. f->f_type = DTYPE_SYSTRACE;
  449. f->f_ops = &systracefops;
  450. f->f_data = (caddr_t) fst;
  451. *(int *)data = fd;
  452. FILE_SET_MATURE(f, p);
  453. break;
  454. default:
  455. error = EINVAL;
  456. break;
  457. }
  458. return (error);
  459. }
  460. void
  461. systrace_wakeup(struct fsystrace *fst)
  462. {
  463. wakeup((caddr_t)fst);
  464. selwakeup(&fst->si);
  465. }
  466. struct proc *
  467. systrace_find(struct str_process *strp)
  468. {
  469. struct proc *proc;
  470. if ((proc = pfind(strp->pid)) == NULL)
  471. return (NULL);
  472. if (proc != strp->proc)
  473. return (NULL);
  474. if (!ISSET(proc->p_flag, P_SYSTRACE))
  475. return (NULL);
  476. return (proc);
  477. }
  478. void
  479. systrace_exit(struct proc *proc)
  480. {
  481. struct str_process *strp;
  482. struct fsystrace *fst;
  483. systrace_lock();
  484. strp = proc->p_systrace;
  485. if (strp != NULL) {
  486. fst = strp->parent;
  487. rw_enter_write(&fst->lock);
  488. systrace_unlock();
  489. /* Insert Exit message */
  490. systrace_msg_child(fst, strp, -1);
  491. systrace_detach(strp);
  492. proc->p_systrace = NULL;
  493. rw_exit_write(&fst->lock);
  494. } else
  495. systrace_unlock();
  496. atomic_clearbits_int(&proc->p_flag, P_SYSTRACE);
  497. }
  498. struct str_process *
  499. systrace_getproc(void)
  500. {
  501. struct str_process *newstrp;
  502. newstrp = pool_get(&systr_proc_pl, PR_WAITOK|PR_ZERO);
  503. newstrp->firstmsg = pool_get(&systr_proc_pl, PR_WAITOK|PR_ZERO);
  504. return (newstrp);
  505. }
  506. void
  507. systrace_freeproc(struct str_process *strp)
  508. {
  509. if (strp->firstmsg)
  510. pool_put(&systr_proc_pl, strp->firstmsg);
  511. pool_put(&systr_proc_pl, strp);
  512. }
  513. void
  514. systrace_fork(struct proc *oldproc, struct proc *p, struct str_process *newstrp)
  515. {
  516. struct str_process *oldstrp, *strp;
  517. struct fsystrace *fst;
  518. systrace_lock();
  519. oldstrp = oldproc->p_systrace;
  520. if (oldstrp == NULL) {
  521. systrace_unlock();
  522. systrace_freeproc(newstrp);
  523. return;
  524. }
  525. fst = oldstrp->parent;
  526. rw_enter_write(&fst->lock);
  527. systrace_unlock();
  528. systrace_insert_process(fst, p, newstrp);
  529. if ((strp = systrace_findpid(fst, p->p_pid)) == NULL)
  530. panic("systrace_fork");
  531. /* Reference policy */
  532. if ((strp->policy = oldstrp->policy) != NULL)
  533. strp->policy->refcount++;
  534. /* Insert fork message */
  535. systrace_msg_child(fst, oldstrp, p->p_pid);
  536. rw_exit_write(&fst->lock);
  537. }
  538. #define REACQUIRE_LOCK do { \
  539. systrace_lock(); \
  540. strp = p->p_systrace; \
  541. if (strp == NULL) { \
  542. systrace_unlock(); \
  543. return (error); \
  544. } \
  545. fst = strp->parent; \
  546. rw_enter_write(&fst->lock); \
  547. systrace_unlock(); \
  548. } while (0)
  549. int
  550. systrace_redirect(int code, struct proc *p, void *v, register_t *retval)
  551. {
  552. struct process *pr = p->p_p;
  553. struct sysent *callp;
  554. struct str_process *strp;
  555. struct str_policy *strpolicy;
  556. struct fsystrace *fst = NULL;
  557. struct emul *oldemul;
  558. int policy, error = 0, report = 0, maycontrol = 0, issuser = 0;
  559. uid_t old_ruid = p->p_ucred->cr_ruid;
  560. gid_t old_rgid = p->p_ucred->cr_rgid;
  561. systrace_lock();
  562. strp = p->p_systrace;
  563. if (strp == NULL) {
  564. systrace_unlock();
  565. return (EINVAL);
  566. }
  567. if (code < 0 || code >= pr->ps_emul->e_nsysent) {
  568. systrace_unlock();
  569. return (EINVAL);
  570. }
  571. KASSERT(strp->proc == p);
  572. fst = strp->parent;
  573. rw_enter_write(&fst->lock);
  574. systrace_unlock();
  575. /*
  576. * We can not monitor a SUID process unless we are root,
  577. * but we wait until it executes something unprivileged.
  578. * A non-root user may only monitor if the real uid and
  579. * real gid match the monitored process. Changing the
  580. * uid or gid causes PS_SUGID to be set.
  581. */
  582. if (fst->issuser) {
  583. maycontrol = 1;
  584. issuser = 1;
  585. } else if (!ISSET(pr->ps_flags, PS_SUGID | PS_SUGIDEXEC)) {
  586. maycontrol = fst->p_ruid == old_ruid &&
  587. fst->p_rgid == old_rgid;
  588. }
  589. if (!maycontrol) {
  590. policy = SYSTR_POLICY_PERMIT;
  591. } else {
  592. /* Find out current policy */
  593. if ((strpolicy = strp->policy) == NULL)
  594. policy = SYSTR_POLICY_ASK;
  595. else {
  596. if (code >= strpolicy->nsysent)
  597. policy = SYSTR_POLICY_NEVER;
  598. else
  599. policy = strpolicy->sysent[code];
  600. }
  601. }
  602. callp = pr->ps_emul->e_sysent + code;
  603. /* Fast-path */
  604. if (policy != SYSTR_POLICY_ASK) {
  605. if (policy != SYSTR_POLICY_PERMIT &&
  606. policy != SYSTR_POLICY_KILL) {
  607. if (policy > 0)
  608. error = policy;
  609. else
  610. error = EPERM;
  611. }
  612. systrace_replacefree(strp);
  613. rw_exit_write(&fst->lock);
  614. if (policy == SYSTR_POLICY_KILL) {
  615. error = EPERM;
  616. DPRINTF(("systrace: pid %u killed on syscall %d\n",
  617. pr->ps_pid, code));
  618. psignal(p, SIGKILL);
  619. } else if (policy == SYSTR_POLICY_PERMIT)
  620. error = (*callp->sy_call)(p, v, retval);
  621. return (error);
  622. }
  623. /*
  624. * Reset our stackgap allocation. Note that when resetting
  625. * the stackgap allocation, we expect to get the same address
  626. * base; i.e. that stackgap_init() is idempotent.
  627. */
  628. systrace_inject(strp, 0 /* Just reset internal state */);
  629. strp->sg = stackgap_init(p);
  630. /* Puts the current process to sleep, return unlocked */
  631. error = systrace_msg_ask(fst, strp, code, callp->sy_argsize, v);
  632. /* lock has been released in systrace_msg_ask() */
  633. if (error)
  634. return (error);
  635. /* We might have detached by now for some reason */
  636. systrace_lock();
  637. if ((strp = p->p_systrace) == NULL) {
  638. systrace_unlock();
  639. return (error);
  640. }
  641. fst = strp->parent;
  642. rw_enter_write(&fst->lock);
  643. systrace_unlock();
  644. if (strp->answer == SYSTR_POLICY_NEVER) {
  645. error = strp->error;
  646. systrace_replacefree(strp);
  647. goto out_unlock;
  648. }
  649. if (ISSET(strp->flags, STR_PROC_SYSCALLRES)) {
  650. CLR(strp->flags, STR_PROC_SYSCALLRES);
  651. report = 1;
  652. }
  653. error = systrace_inject(strp, 1/* Perform copies */);
  654. /* Replace the arguments if necessary */
  655. if (!error && strp->replace != NULL)
  656. error = systrace_replace(strp, callp->sy_argsize, v);
  657. if (error)
  658. goto out_unlock;
  659. oldemul = pr->ps_emul;
  660. /* Elevate privileges as desired */
  661. if (issuser && ISSET(strp->flags, STR_PROC_SETEUID|STR_PROC_SETEGID)) {
  662. struct ucred *uc, *newcred;
  663. uc = p->p_ucred;
  664. newcred = NULL;
  665. if (ISSET(strp->flags, STR_PROC_SETEUID) &&
  666. uc->cr_uid != strp->seteuid) {
  667. newcred = crdup(uc);
  668. newcred->cr_uid = strp->seteuid;
  669. }
  670. if (ISSET(strp->flags, STR_PROC_SETEGID) &&
  671. uc->cr_gid != strp->setegid) {
  672. if (newcred == NULL)
  673. newcred = crdup(uc);
  674. newcred->cr_gid = strp->setegid;
  675. }
  676. if (newcred != NULL) {
  677. p->p_ucred = newcred;
  678. crfree(uc);
  679. atomic_setbits_int(&pr->ps_flags, PS_SUGID);
  680. }
  681. }
  682. rw_exit_write(&fst->lock);
  683. error = (*callp->sy_call)(p, v, retval);
  684. /* reset the credentials on the thread */
  685. refreshcreds(p);
  686. /* Return to old privileges */
  687. systrace_lock();
  688. if ((strp = p->p_systrace) == NULL) {
  689. systrace_unlock();
  690. return (error);
  691. }
  692. systrace_replacefree(strp);
  693. if (ISSET(pr->ps_flags, PS_SUGID | PS_SUGIDEXEC)) {
  694. if ((fst = strp->parent) == NULL || !fst->issuser) {
  695. systrace_unlock();
  696. return (error);
  697. }
  698. }
  699. /* Report change in emulation */
  700. /* See if we should force a report */
  701. if (ISSET(strp->flags, STR_PROC_REPORT)) {
  702. CLR(strp->flags, STR_PROC_REPORT);
  703. oldemul = NULL;
  704. }
  705. /* Acquire lock */
  706. fst = strp->parent;
  707. rw_enter_write(&fst->lock);
  708. systrace_unlock();
  709. if (pr->ps_emul != oldemul) {
  710. /* Old policy is without meaning now */
  711. if (strp->policy) {
  712. systrace_closepolicy(fst, strp->policy);
  713. strp->policy = NULL;
  714. }
  715. systrace_msg_emul(fst, strp);
  716. REACQUIRE_LOCK;
  717. }
  718. /* Report if effective uid or gid changed */
  719. if (old_ruid != pr->ps_ucred->cr_ruid ||
  720. old_rgid != pr->ps_ucred->cr_rgid) {
  721. systrace_msg_ugid(fst, strp);
  722. REACQUIRE_LOCK;
  723. }
  724. /* Report result from system call */
  725. if (report) {
  726. systrace_msg_result(fst, strp, error, code,
  727. callp->sy_argsize, v, retval);
  728. /* not locked */
  729. goto out;
  730. }
  731. out_unlock:
  732. rw_exit_write(&fst->lock);
  733. out:
  734. return (error);
  735. }
  736. /* Called with fst locked */
  737. int
  738. systrace_answer(struct str_process *strp, struct systrace_answer *ans)
  739. {
  740. int error = 0;
  741. DPRINTF(("%s: %u: policy %d\n", __func__,
  742. ans->stra_pid, ans->stra_policy));
  743. if (!POLICY_VALID(ans->stra_policy)) {
  744. error = EINVAL;
  745. goto out;
  746. }
  747. /* Check if answer is in sync with us */
  748. if (ans->stra_seqnr != strp->seqnr) {
  749. error = ESRCH;
  750. goto out;
  751. }
  752. if ((error = systrace_processready(strp)) != 0)
  753. goto out;
  754. strp->answer = ans->stra_policy;
  755. strp->error = ans->stra_error;
  756. if (!strp->error)
  757. strp->error = EPERM;
  758. if (ISSET(ans->stra_flags, SYSTR_FLAGS_RESULT))
  759. SET(strp->flags, STR_PROC_SYSCALLRES);
  760. /* See if we should elevate privileges for this system call */
  761. if (ISSET(ans->stra_flags, SYSTR_FLAGS_SETEUID)) {
  762. SET(strp->flags, STR_PROC_SETEUID);
  763. strp->seteuid = ans->stra_seteuid;
  764. }
  765. if (ISSET(ans->stra_flags, SYSTR_FLAGS_SETEGID)) {
  766. SET(strp->flags, STR_PROC_SETEGID);
  767. strp->setegid = ans->stra_setegid;
  768. }
  769. /* Clearing the flag indicates to the process that it woke up */
  770. CLR(strp->flags, STR_PROC_WAITANSWER);
  771. wakeup(strp);
  772. out:
  773. return (error);
  774. }
  775. int
  776. systrace_setscriptname(struct str_process *strp, struct systrace_scriptname *ans)
  777. {
  778. strlcpy(strp->scriptname,
  779. ans->sn_scriptname, sizeof(strp->scriptname));
  780. return (0);
  781. }
  782. int
  783. systrace_inject(struct str_process *strp, int docopy)
  784. {
  785. int ind, ret = 0;
  786. for (ind = 0; ind < strp->injectind; ind++) {
  787. struct str_inject *inject = &strp->injects[ind];
  788. if (!ret && docopy &&
  789. copyout(inject->kaddr, inject->uaddr, inject->len))
  790. ret = EINVAL;
  791. free(inject->kaddr, M_XDATA, 0);
  792. }
  793. strp->injectind = 0;
  794. return (ret);
  795. }
  796. int
  797. systrace_prepinject(struct str_process *strp, struct systrace_inject *inj)
  798. {
  799. caddr_t udata, kaddr = NULL;
  800. int ret = 0;
  801. struct str_inject *inject;
  802. if (strp->injectind >= SYSTR_MAXINJECTS)
  803. return (ENOBUFS);
  804. udata = stackgap_alloc(&strp->sg, inj->stri_len);
  805. if (udata == NULL)
  806. return (ENOMEM);
  807. /*
  808. * We have infact forced a maximum length on stri_len because
  809. * of the stackgap.
  810. */
  811. kaddr = malloc(inj->stri_len, M_XDATA, M_WAITOK);
  812. ret = copyin(inj->stri_addr, kaddr, inj->stri_len);
  813. if (ret) {
  814. free(kaddr, M_XDATA, 0);
  815. return (ret);
  816. }
  817. inject = &strp->injects[strp->injectind++];
  818. inject->kaddr = kaddr;
  819. inject->uaddr = inj->stri_addr = udata;
  820. inject->len = inj->stri_len;
  821. return (0);
  822. }
  823. int
  824. systrace_policy(struct fsystrace *fst, struct systrace_policy *pol)
  825. {
  826. struct str_policy *strpol;
  827. struct str_process *strp;
  828. switch(pol->strp_op) {
  829. case SYSTR_POLICY_NEW:
  830. DPRINTF(("%s: new, ents %d\n", __func__,
  831. pol->strp_maxents));
  832. if (pol->strp_maxents <= 0 || pol->strp_maxents > 1024)
  833. return (EINVAL);
  834. strpol = systrace_newpolicy(fst, pol->strp_maxents);
  835. if (strpol == NULL)
  836. return (ENOBUFS);
  837. pol->strp_num = strpol->nr;
  838. break;
  839. case SYSTR_POLICY_ASSIGN:
  840. DPRINTF(("%s: %d -> pid %d\n", __func__,
  841. pol->strp_num, pol->strp_pid));
  842. /* Find right policy by number */
  843. TAILQ_FOREACH(strpol, &fst->policies, next)
  844. if (strpol->nr == pol->strp_num)
  845. break;
  846. if (strpol == NULL)
  847. return (EINVAL);
  848. strp = systrace_findpid(fst, pol->strp_pid);
  849. if (strp == NULL)
  850. return (EINVAL);
  851. /* Check that emulation matches */
  852. if (strpol->emul && strpol->emul != strp->proc->p_p->ps_emul)
  853. return (EINVAL);
  854. if (strp->policy)
  855. systrace_closepolicy(fst, strp->policy);
  856. strp->policy = strpol;
  857. /* LRU for policy use */
  858. TAILQ_REMOVE(&fst->policies, strpol, next);
  859. TAILQ_INSERT_TAIL(&fst->policies, strpol, next);
  860. strpol->refcount++;
  861. /* Record emulation for this policy */
  862. if (strpol->emul == NULL)
  863. strpol->emul = strp->proc->p_p->ps_emul;
  864. break;
  865. case SYSTR_POLICY_MODIFY:
  866. DPRINTF(("%s: %d: code %d -> policy %d\n", __func__,
  867. pol->strp_num, pol->strp_code, pol->strp_policy));
  868. if (!POLICY_VALID(pol->strp_policy))
  869. return (EINVAL);
  870. TAILQ_FOREACH(strpol, &fst->policies, next)
  871. if (strpol->nr == pol->strp_num)
  872. break;
  873. if (strpol == NULL)
  874. return (EINVAL);
  875. if (pol->strp_code < 0 || pol->strp_code >= strpol->nsysent)
  876. return (EINVAL);
  877. strpol->sysent[pol->strp_code] = pol->strp_policy;
  878. break;
  879. default:
  880. return (EINVAL);
  881. }
  882. return (0);
  883. }
  884. int
  885. systrace_processready(struct str_process *strp)
  886. {
  887. if (ISSET(strp->flags, STR_PROC_ONQUEUE))
  888. return (EBUSY);
  889. if (!ISSET(strp->flags, STR_PROC_WAITANSWER))
  890. return (EBUSY);
  891. if (strp->proc->p_stat != SSLEEP)
  892. return (EBUSY);
  893. return (0);
  894. }
  895. int
  896. systrace_getcwd(struct fsystrace *fst, struct str_process *strp, int atfd)
  897. {
  898. struct filedesc *myfdp, *fdp;
  899. struct vnode *dvp, *odvp;
  900. int error;
  901. DPRINTF(("%s: %d\n", __func__, strp->pid));
  902. error = systrace_processready(strp);
  903. if (error)
  904. return (error);
  905. myfdp = curproc->p_fd;
  906. fdp = strp->proc->p_fd;
  907. if (myfdp == NULL || fdp == NULL)
  908. return (EINVAL);
  909. if (atfd == AT_FDCWD)
  910. dvp = fdp->fd_cdir;
  911. else {
  912. struct file *fp = fd_getfile(fdp, atfd);
  913. if (fp == NULL || fp->f_type != DTYPE_VNODE)
  914. return (EINVAL);
  915. dvp = (struct vnode *)fp->f_data;
  916. if (dvp->v_type != VDIR)
  917. return (EINVAL);
  918. }
  919. /* Is there a STRIOCGETCWD currently in effect? */
  920. if (fst->fd_pid == 0) {
  921. /* nope: just save the current values */
  922. fst->fd_cdir = myfdp->fd_cdir;
  923. fst->fd_rdir = myfdp->fd_rdir;
  924. } else {
  925. /* yep: carefully release the current values */
  926. odvp = myfdp->fd_rdir;
  927. myfdp->fd_rdir = fst->fd_rdir;
  928. if (odvp != NULL)
  929. vrele(odvp);
  930. odvp = myfdp->fd_cdir;
  931. myfdp->fd_cdir = fst->fd_cdir;
  932. if (odvp != NULL)
  933. vrele(odvp);
  934. }
  935. fst->fd_pid = strp->pid;
  936. if ((myfdp->fd_cdir = dvp) != NULL)
  937. vref(myfdp->fd_cdir);
  938. if ((myfdp->fd_rdir = fdp->fd_rdir) != NULL)
  939. vref(myfdp->fd_rdir);
  940. return (0);
  941. }
  942. int
  943. systrace_restorecwd(struct fsystrace *fst, struct proc *p)
  944. {
  945. struct filedesc *fdp;
  946. struct vnode *rvp, *cvp;
  947. if (!fst->fd_pid)
  948. return (EINVAL);
  949. fdp = p->p_fd;
  950. /*
  951. * Restore original root and current directories and release the
  952. * ones from the other process.
  953. */
  954. rvp = fdp->fd_rdir;
  955. cvp = fdp->fd_cdir;
  956. fdp->fd_rdir = fst->fd_rdir;
  957. fdp->fd_cdir = fst->fd_cdir;
  958. fst->fd_cdir = fst->fd_rdir = NULL;
  959. if (rvp != NULL)
  960. vrele(rvp);
  961. if (cvp != NULL)
  962. vrele(cvp);
  963. /* Note that we are normal again */
  964. fst->fd_pid = 0;
  965. return (0);
  966. }
  967. int
  968. systrace_io(struct str_process *strp, struct systrace_io *io)
  969. {
  970. struct proc *p = curproc, *t = strp->proc;
  971. struct uio uio;
  972. struct iovec iov;
  973. int error = 0;
  974. DPRINTF(("%s: %u: %p(%lu)\n", __func__,
  975. io->strio_pid, io->strio_offs, (u_long)io->strio_len));
  976. switch (io->strio_op) {
  977. case SYSTR_READ:
  978. uio.uio_rw = UIO_READ;
  979. break;
  980. case SYSTR_WRITE:
  981. uio.uio_rw = UIO_WRITE;
  982. break;
  983. default:
  984. return (EINVAL);
  985. }
  986. error = systrace_processready(strp);
  987. if (error)
  988. goto out;
  989. iov.iov_base = io->strio_addr;
  990. iov.iov_len = io->strio_len;
  991. uio.uio_iov = &iov;
  992. uio.uio_iovcnt = 1;
  993. uio.uio_offset = (off_t)(u_long)io->strio_offs;
  994. uio.uio_resid = io->strio_len;
  995. uio.uio_segflg = UIO_USERSPACE;
  996. uio.uio_procp = p;
  997. error = process_domem(p, t, &uio, PT_WRITE_I);
  998. io->strio_len -= uio.uio_resid;
  999. out:
  1000. return (error);
  1001. }
  1002. int
  1003. systrace_attach(struct fsystrace *fst, pid_t pid)
  1004. {
  1005. int error = 0;
  1006. struct proc *p = curproc;
  1007. struct proc *t; /* target thread */
  1008. struct process *tr; /* target process */
  1009. struct str_process *newstrp;
  1010. if ((t = pfind(pid)) == NULL || (t->p_flag & P_THREAD)) {
  1011. error = ESRCH;
  1012. goto out;
  1013. }
  1014. tr = t->p_p;
  1015. if (ISSET(tr->ps_flags, PS_INEXEC)) {
  1016. error = EAGAIN;
  1017. goto out;
  1018. }
  1019. /*
  1020. * You can't attach to a process if:
  1021. * (1) it's the process that's doing the attaching,
  1022. */
  1023. if (tr == p->p_p) {
  1024. error = EINVAL;
  1025. goto out;
  1026. }
  1027. /*
  1028. * (2) it's a system process
  1029. */
  1030. if (ISSET(t->p_flag, P_SYSTEM)) {
  1031. error = EPERM;
  1032. goto out;
  1033. }
  1034. /*
  1035. * (3) it's being traced already
  1036. */
  1037. if (ISSET(t->p_flag, P_SYSTRACE)) {
  1038. error = EBUSY;
  1039. goto out;
  1040. }
  1041. /*
  1042. * (4) it's not owned by you, or the last exec
  1043. * gave us setuid/setgid privs (unless
  1044. * you're root), or...
  1045. *
  1046. * [Note: once PS_SUGID or PS_SUGIDEXEC gets set in execve(),
  1047. * it stays set until the process does another execve(). Hence
  1048. * this prevents a setuid process which revokes its
  1049. * special privileges using setuid() from being
  1050. * traced. This is good security.]
  1051. */
  1052. if ((tr->ps_ucred->cr_ruid != p->p_ucred->cr_ruid ||
  1053. ISSET(tr->ps_flags, PS_SUGID | PS_SUGIDEXEC)) &&
  1054. (error = suser(p, 0)) != 0)
  1055. goto out;
  1056. /*
  1057. * (5) ...it's init, which controls the security level
  1058. * of the entire system, and the system was not
  1059. * compiled with permanently insecure mode turned
  1060. * on.
  1061. */
  1062. if ((tr->ps_pid == 1) && (securelevel > -1)) {
  1063. error = EPERM;
  1064. goto out;
  1065. }
  1066. newstrp = systrace_getproc();
  1067. systrace_insert_process(fst, t, newstrp);
  1068. out:
  1069. return (error);
  1070. }
  1071. void
  1072. systrace_execve0(struct proc *p)
  1073. {
  1074. struct str_process *strp;
  1075. systrace_lock();
  1076. strp = p->p_systrace;
  1077. strp->isscript = 0;
  1078. systrace_unlock();
  1079. }
  1080. void
  1081. systrace_execve1(char *path, struct proc *p)
  1082. {
  1083. struct str_process *strp;
  1084. struct fsystrace *fst;
  1085. struct str_msg_execve *msg_execve;
  1086. do {
  1087. systrace_lock();
  1088. strp = p->p_systrace;
  1089. if (strp == NULL) {
  1090. systrace_unlock();
  1091. return;
  1092. }
  1093. msg_execve = &strp->msg.msg_data.msg_execve;
  1094. fst = strp->parent;
  1095. rw_enter_write(&fst->lock);
  1096. systrace_unlock();
  1097. /*
  1098. * susers will get the execve call anyway. Also, if
  1099. * we're not allowed to control the process, escape.
  1100. */
  1101. if (fst->issuser ||
  1102. fst->p_ruid != p->p_ucred->cr_ruid ||
  1103. fst->p_rgid != p->p_ucred->cr_rgid) {
  1104. rw_exit_write(&fst->lock);
  1105. return;
  1106. }
  1107. strlcpy(msg_execve->path, path, MAXPATHLEN);
  1108. } while (systrace_make_msg(strp, SYSTR_MSG_EXECVE) != 0);
  1109. }
  1110. /* Prepare to replace arguments */
  1111. int
  1112. systrace_preprepl(struct str_process *strp, struct systrace_replace *repl)
  1113. {
  1114. size_t len;
  1115. int i, ret = 0;
  1116. ret = systrace_processready(strp);
  1117. if (ret)
  1118. return (ret);
  1119. if (strp->replace != NULL) {
  1120. free(strp->replace, M_XDATA, 0);
  1121. strp->replace = NULL;
  1122. }
  1123. if (repl->strr_nrepl < 0 || repl->strr_nrepl > SYSTR_MAXARGS)
  1124. return (EINVAL);
  1125. for (i = 0, len = 0; i < repl->strr_nrepl; i++) {
  1126. if (repl->strr_argind[i] < 0 ||
  1127. repl->strr_argind[i] >= SYSTR_MAXARGS)
  1128. return (EINVAL);
  1129. if (repl->strr_offlen[i] == 0)
  1130. continue;
  1131. len += repl->strr_offlen[i];
  1132. if (repl->strr_offlen[i] > SYSTR_MAXREPLEN ||
  1133. repl->strr_off[i] > SYSTR_MAXREPLEN ||
  1134. len > SYSTR_MAXREPLEN)
  1135. return (EINVAL);
  1136. if (repl->strr_offlen[i] + repl->strr_off[i] > len)
  1137. return (EINVAL);
  1138. }
  1139. /* Make sure that the length adds up */
  1140. if (repl->strr_len != len)
  1141. return (EINVAL);
  1142. /* Check against a maximum length */
  1143. if (repl->strr_len > SYSTR_MAXREPLEN)
  1144. return (EINVAL);
  1145. strp->replace = (struct systrace_replace *)
  1146. malloc(sizeof(struct systrace_replace) + len, M_XDATA, M_WAITOK);
  1147. memcpy(strp->replace, repl, sizeof(struct systrace_replace));
  1148. ret = copyin(repl->strr_base, strp->replace + 1, len);
  1149. if (ret) {
  1150. free(strp->replace, M_XDATA, 0);
  1151. strp->replace = NULL;
  1152. return (ret);
  1153. }
  1154. /* Adjust the offset */
  1155. repl = strp->replace;
  1156. repl->strr_base = (caddr_t)(repl + 1);
  1157. return (0);
  1158. }
  1159. /*
  1160. * Replace the arguments with arguments from the monitoring process.
  1161. */
  1162. int
  1163. systrace_replace(struct str_process *strp, size_t argsize, register_t args[])
  1164. {
  1165. struct systrace_replace *repl = strp->replace;
  1166. caddr_t kdata, kbase;
  1167. caddr_t udata, ubase;
  1168. int i, maxarg, ind, ret = 0;
  1169. maxarg = argsize/sizeof(register_t);
  1170. ubase = stackgap_alloc(&strp->sg, repl->strr_len);
  1171. if (ubase == NULL) {
  1172. ret = EINVAL;
  1173. goto out;
  1174. }
  1175. kbase = repl->strr_base;
  1176. for (i = 0; i < maxarg && i < repl->strr_nrepl; i++) {
  1177. ind = repl->strr_argind[i];
  1178. if (ind < 0 || ind >= maxarg) {
  1179. ret = EINVAL;
  1180. goto out;
  1181. }
  1182. if (repl->strr_offlen[i] == 0) {
  1183. args[ind] = repl->strr_off[i];
  1184. continue;
  1185. }
  1186. kdata = kbase + repl->strr_off[i];
  1187. if (repl->strr_flags[i] & SYSTR_NOLINKS) {
  1188. ret = systrace_fname(strp, kdata, repl->strr_offlen[i]);
  1189. if (ret != 0)
  1190. goto out;
  1191. }
  1192. udata = ubase + repl->strr_off[i];
  1193. if (copyout(kdata, udata, repl->strr_offlen[i])) {
  1194. ret = EINVAL;
  1195. goto out;
  1196. }
  1197. /* Replace the argument with the new address */
  1198. args[ind] = (register_t)udata;
  1199. }
  1200. out:
  1201. return (ret);
  1202. }
  1203. int
  1204. systrace_fname(struct str_process *strp, caddr_t kdata, size_t len)
  1205. {
  1206. if (strp->nfname >= SYSTR_MAXFNAME || len < 1)
  1207. return EINVAL;
  1208. strp->fname[strp->nfname] = kdata;
  1209. strp->fname[strp->nfname][len - 1] = '\0';
  1210. strp->nfname++;
  1211. return 0;
  1212. }
  1213. void
  1214. systrace_replacefree(struct str_process *strp)
  1215. {
  1216. if (strp->replace != NULL) {
  1217. free(strp->replace, M_XDATA, 0);
  1218. strp->replace = NULL;
  1219. }
  1220. while (strp->nfname > 0) {
  1221. strp->nfname--;
  1222. strp->fname[strp->nfname] = NULL;
  1223. }
  1224. }
  1225. int
  1226. systrace_scriptname(struct proc *p, char *dst)
  1227. {
  1228. struct str_process *strp;
  1229. struct fsystrace *fst;
  1230. int error = 0;
  1231. systrace_lock();
  1232. strp = p->p_systrace;
  1233. fst = strp->parent;
  1234. rw_enter_write(&fst->lock);
  1235. systrace_unlock();
  1236. if (!fst->issuser &&
  1237. (ISSET(p->p_p->ps_flags, PS_SUGID | PS_SUGIDEXEC) ||
  1238. fst->p_ruid != p->p_ucred->cr_ruid ||
  1239. fst->p_rgid != p->p_ucred->cr_rgid)) {
  1240. error = EPERM;
  1241. goto out;
  1242. }
  1243. if (strp != NULL) {
  1244. if (strp->scriptname[0] == '\0') {
  1245. error = ENOENT;
  1246. goto out;
  1247. }
  1248. strlcpy(dst, strp->scriptname, MAXPATHLEN);
  1249. strp->isscript = 1;
  1250. }
  1251. out:
  1252. strp->scriptname[0] = '\0';
  1253. rw_exit_write(&fst->lock);
  1254. return (error);
  1255. }
  1256. void
  1257. systrace_namei(struct nameidata *ndp)
  1258. {
  1259. struct str_process *strp;
  1260. struct fsystrace *fst;
  1261. struct componentname *cnp = &ndp->ni_cnd;
  1262. size_t i;
  1263. int hamper = 0;
  1264. systrace_lock();
  1265. strp = cnp->cn_proc->p_systrace;
  1266. if (strp != NULL) {
  1267. fst = strp->parent;
  1268. rw_enter_write(&fst->lock);
  1269. systrace_unlock();
  1270. for (i = 0; i < strp->nfname; i++)
  1271. if (strcmp(cnp->cn_pnbuf, strp->fname[i]) == 0) {
  1272. hamper = 1;
  1273. break;
  1274. }
  1275. if (!hamper && strp->isscript &&
  1276. strcmp(cnp->cn_pnbuf, strp->scriptname) == 0)
  1277. hamper = 1;
  1278. rw_exit_write(&fst->lock);
  1279. } else
  1280. systrace_unlock();
  1281. if (hamper) {
  1282. /* ELOOP if namei() tries to readlink */
  1283. ndp->ni_loopcnt = SYMLOOP_MAX;
  1284. cnp->cn_flags &= ~FOLLOW;
  1285. cnp->cn_flags |= NOFOLLOW;
  1286. }
  1287. }
  1288. struct str_process *
  1289. systrace_findpid(struct fsystrace *fst, pid_t pid)
  1290. {
  1291. struct str_process *strp;
  1292. struct proc *proc = NULL;
  1293. TAILQ_FOREACH(strp, &fst->processes, next)
  1294. if (strp->pid == pid)
  1295. break;
  1296. if (strp == NULL)
  1297. return (NULL);
  1298. proc = systrace_find(strp);
  1299. return (proc ? strp : NULL);
  1300. }
  1301. int
  1302. systrace_detach(struct str_process *strp)
  1303. {
  1304. struct proc *proc;
  1305. struct fsystrace *fst = NULL;
  1306. int error = 0;
  1307. DPRINTF(("%s: Trying to detach from %d\n", __func__, strp->pid));
  1308. if ((proc = systrace_find(strp)) != NULL) {
  1309. atomic_clearbits_int(&proc->p_flag, P_SYSTRACE);
  1310. proc->p_systrace = NULL;
  1311. } else
  1312. error = ESRCH;
  1313. if (ISSET(strp->flags, STR_PROC_WAITANSWER)) {
  1314. CLR(strp->flags, STR_PROC_WAITANSWER);
  1315. wakeup(strp);
  1316. }
  1317. fst = strp->parent;
  1318. systrace_wakeup(fst);
  1319. if (ISSET(strp->flags, STR_PROC_ONQUEUE))
  1320. TAILQ_REMOVE(&fst->messages, strp, msg_next);
  1321. TAILQ_REMOVE(&fst->processes, strp, next);
  1322. fst->nprocesses--;
  1323. if (strp->policy)
  1324. systrace_closepolicy(fst, strp->policy);
  1325. systrace_replacefree(strp);
  1326. systrace_freeproc(strp);
  1327. return (error);
  1328. }
  1329. void
  1330. systrace_closepolicy(struct fsystrace *fst, struct str_policy *policy)
  1331. {
  1332. if (--policy->refcount)
  1333. return;
  1334. fst->npolicies--;
  1335. if (policy->nsysent)
  1336. free(policy->sysent, M_XDATA, 0);
  1337. TAILQ_REMOVE(&fst->policies, policy, next);
  1338. pool_put(&systr_policy_pl, policy);
  1339. }
  1340. void
  1341. systrace_insert_process(struct fsystrace *fst, struct proc *proc,
  1342. struct str_process *strp)
  1343. {
  1344. strp->pid = proc->p_pid;
  1345. strp->proc = proc;
  1346. strp->parent = fst;
  1347. TAILQ_INSERT_TAIL(&fst->processes, strp, next);
  1348. fst->nprocesses++;
  1349. proc->p_systrace = strp;
  1350. atomic_setbits_int(&proc->p_flag, P_SYSTRACE);
  1351. }
  1352. struct str_policy *
  1353. systrace_newpolicy(struct fsystrace *fst, int maxents)
  1354. {
  1355. struct str_policy *pol;
  1356. int i;
  1357. if (fst->npolicies > SYSTR_MAX_POLICIES && !fst->issuser) {
  1358. struct str_policy *tmp;
  1359. /* Try to find a policy for freeing */
  1360. TAILQ_FOREACH(tmp, &fst->policies, next) {
  1361. if (tmp->refcount == 1)
  1362. break;
  1363. }
  1364. if (tmp == NULL)
  1365. return (NULL);
  1366. /* Notify userland about freed policy */
  1367. systrace_msg_policyfree(fst, tmp);
  1368. /* Free this policy */
  1369. systrace_closepolicy(fst, tmp);
  1370. }
  1371. pol = pool_get(&systr_policy_pl, PR_NOWAIT|PR_ZERO);
  1372. if (pol == NULL)
  1373. return (NULL);
  1374. DPRINTF(("%s: allocating %d -> %lu\n", __func__,
  1375. maxents, (u_long)maxents * sizeof(int)));
  1376. pol->sysent = malloc(maxents, M_XDATA, M_WAITOK);
  1377. pol->nsysent = maxents;
  1378. for (i = 0; i < maxents; i++)
  1379. pol->sysent[i] = SYSTR_POLICY_ASK;
  1380. fst->npolicies++;
  1381. pol->nr = fst->npolicynr++;
  1382. pol->refcount = 1;
  1383. TAILQ_INSERT_TAIL(&fst->policies, pol, next);
  1384. return (pol);
  1385. }
  1386. int
  1387. systrace_msg_ask(struct fsystrace *fst, struct str_process *strp,
  1388. int code, size_t argsize, register_t args[])
  1389. {
  1390. struct str_msg_ask *msg_ask = &strp->msg.msg_data.msg_ask;
  1391. int i;
  1392. msg_ask->code = code;
  1393. msg_ask->argsize = argsize;
  1394. for (i = 0; i < (argsize/sizeof(register_t)) && i < SYSTR_MAXARGS; i++)
  1395. msg_ask->args[i] = args[i];
  1396. return (systrace_make_msg(strp, SYSTR_MSG_ASK));
  1397. }
  1398. int
  1399. systrace_msg_result(struct fsystrace *fst, struct str_process *strp,
  1400. int error, int code, size_t argsize, register_t args[], register_t rval[])
  1401. {
  1402. struct str_msg_ask *msg_ask = &strp->msg.msg_data.msg_ask;
  1403. int i;
  1404. msg_ask->code = code;
  1405. msg_ask->argsize = argsize;
  1406. msg_ask->result = error;
  1407. for (i = 0; i < (argsize/sizeof(register_t)) && i < SYSTR_MAXARGS; i++)
  1408. msg_ask->args[i] = args[i];
  1409. msg_ask->rval[0] = rval[0];
  1410. msg_ask->rval[1] = rval[1];
  1411. return (systrace_make_msg(strp, SYSTR_MSG_RES));
  1412. }
  1413. int
  1414. systrace_msg_emul(struct fsystrace *fst, struct str_process *strp)
  1415. {
  1416. struct str_msg_emul *msg_emul = &strp->msg.msg_data.msg_emul;
  1417. struct proc *p = strp->proc;
  1418. memcpy(msg_emul->emul, p->p_p->ps_emul->e_name, SYSTR_EMULEN);
  1419. return (systrace_make_msg(strp, SYSTR_MSG_EMUL));
  1420. }
  1421. int
  1422. systrace_msg_ugid(struct fsystrace *fst, struct str_process *strp)
  1423. {
  1424. struct str_msg_ugid *msg_ugid = &strp->msg.msg_data.msg_ugid;
  1425. struct ucred *uc = strp->proc->p_p->ps_ucred;
  1426. msg_ugid->uid = uc->cr_ruid;
  1427. msg_ugid->gid = uc->cr_rgid;
  1428. return (systrace_make_msg(strp, SYSTR_MSG_UGID));
  1429. }
  1430. int
  1431. systrace_make_msg(struct str_process *strp, int type)
  1432. {
  1433. struct str_message *msg = &strp->msg;
  1434. struct fsystrace *fst = strp->parent;
  1435. int st, pri;
  1436. pri = PWAIT|PCATCH;
  1437. if (type == SYSTR_MSG_EXECVE)
  1438. pri &= ~PCATCH;
  1439. msg->msg_seqnr = ++strp->seqnr;
  1440. msg->msg_type = type;
  1441. msg->msg_pid = strp->pid;
  1442. if (strp->policy)
  1443. msg->msg_policy = strp->policy->nr;
  1444. else
  1445. msg->msg_policy = -1;
  1446. SET(strp->flags, STR_PROC_WAITANSWER);
  1447. if (ISSET(strp->flags, STR_PROC_ONQUEUE))
  1448. goto out;
  1449. TAILQ_INSERT_TAIL(&fst->messages, strp, msg_next);
  1450. SET(strp->flags, STR_PROC_ONQUEUE);
  1451. out:
  1452. systrace_wakeup(fst);
  1453. /* Release the lock - XXX */
  1454. rw_exit_write(&fst->lock);
  1455. while (1) {
  1456. st = tsleep(strp, pri, "systrmsg", 0);
  1457. if (st != 0)
  1458. return (ERESTART);
  1459. /* If we detach, then everything is permitted */
  1460. if ((strp = curproc->p_systrace) == NULL)
  1461. return (0);
  1462. if (!ISSET(strp->flags, STR_PROC_WAITANSWER))
  1463. break;
  1464. }
  1465. return (0);
  1466. }
  1467. int
  1468. systrace_msg_child(struct fsystrace *fst, struct str_process *strp, pid_t npid)
  1469. {
  1470. struct str_process *nstrp;
  1471. struct str_message *msg;
  1472. struct str_msg_child *msg_child;
  1473. if (strp->firstmsg) {
  1474. nstrp = strp->firstmsg;
  1475. strp->firstmsg = NULL;
  1476. } else
  1477. nstrp = pool_get(&systr_proc_pl, PR_WAITOK|PR_ZERO);
  1478. DPRINTF(("%s: %p: pid %d -> pid %d\n", __func__,
  1479. nstrp, strp->pid, npid));
  1480. msg = &nstrp->msg;
  1481. msg_child = &msg->msg_data.msg_child;
  1482. msg->msg_type = SYSTR_MSG_CHILD;
  1483. msg->msg_pid = strp->pid;
  1484. if (strp->policy)
  1485. msg->msg_policy = strp->policy->nr;
  1486. else
  1487. msg->msg_policy = -1;
  1488. msg_child->new_pid = npid;
  1489. TAILQ_INSERT_TAIL(&fst->messages, nstrp, msg_next);
  1490. systrace_wakeup(fst);
  1491. return (0);
  1492. }
  1493. int
  1494. systrace_msg_policyfree(struct fsystrace *fst, struct str_policy *strpol)
  1495. {
  1496. struct str_process *nstrp;
  1497. struct str_message *msg;
  1498. nstrp = pool_get(&systr_proc_pl, PR_WAITOK|PR_ZERO);
  1499. DPRINTF(("%s: free %d\n", __func__, strpol->nr));
  1500. msg = &nstrp->msg;
  1501. msg->msg_type = SYSTR_MSG_POLICYFREE;
  1502. msg->msg_policy = strpol->nr;
  1503. TAILQ_INSERT_TAIL(&fst->messages, nstrp, msg_next);
  1504. systrace_wakeup(fst);
  1505. return (0);
  1506. }