From 3253a23b915df9c6e10d586a4a69181c1f1079bc Mon Sep 17 00:00:00 2001 From: Andreas Kling Date: Wed, 24 Oct 2018 00:20:34 +0200 Subject: [PATCH] Add a simplified waitpid() so that sh can wait on spawned commands. --- Kernel/Syscall.cpp | 2 ++ Kernel/Syscall.h | 1 + Kernel/Task.cpp | 33 ++++++++++++++++++++++++++------- Kernel/Task.h | 5 +++++ Kernel/_fs_contents | Bin 1024000 -> 1024000 bytes LibC/unistd.cpp | 5 +++++ LibC/unistd.h | 1 + Userland/sh.cpp | 2 ++ 8 files changed, 42 insertions(+), 7 deletions(-) diff --git a/Kernel/Syscall.cpp b/Kernel/Syscall.cpp index ede05bda5f..a5701b452f 100644 --- a/Kernel/Syscall.cpp +++ b/Kernel/Syscall.cpp @@ -88,6 +88,8 @@ DWORD handle(DWORD function, DWORD arg1, DWORD arg2, DWORD arg3) return current->sys$getgid(); case Syscall::PosixGetpid: return current->sys$getpid(); + case Syscall::PosixWaitpid: + return current->sys$waitpid((pid_t)arg1); case Syscall::PosixExit: cli(); locker.unlock(); diff --git a/Kernel/Syscall.h b/Kernel/Syscall.h index 095fc507e7..edc24d610b 100644 --- a/Kernel/Syscall.h +++ b/Kernel/Syscall.h @@ -23,6 +23,7 @@ enum Function { PosixExit = 0x1991, PosixGetgid = 0x1992, PosixGetpid = 0x1993, + PosixWaitpid = 0x1994, }; void initialize(); diff --git a/Kernel/Task.cpp b/Kernel/Task.cpp index 075c4709a8..6c0ba1d43d 100644 --- a/Kernel/Task.cpp +++ b/Kernel/Task.cpp @@ -11,6 +11,9 @@ #include "MemoryManager.h" //#define DEBUG_IO +//#define TASK_DEBUG + +static const DWORD defaultStackSize = 16384; Task* current; Task* s_kernelTask; @@ -169,7 +172,9 @@ Task* Task::create(const String& path, uid_t uid, gid_t gid) s_tasks->prepend(t); system.nprocess++; +#ifdef TASK_DEBUG kprintf("Task %u (%s) spawned @ %p\n", t->pid(), t->name().characters(), t->m_tss.eip); +#endif sti(); return t; @@ -206,9 +211,6 @@ Task::Task(String&& name, uid_t uid, gid_t gid) m_tss.cr3 = MemoryManager::the().pageDirectoryBase().get(); - // NOTE: Each task gets 16KB of stack. - static const DWORD defaultStackSize = 16384; - auto* region = allocateRegion(defaultStackSize, "stack"); ASSERT(region); m_stackTop = region->linearAddress.offset(defaultStackSize).get() & 0xfffffff8; @@ -287,9 +289,6 @@ Task::Task(void (*e)(), const char* n, IPC::Handle h, RingLevel ring) m_tss.eip = codeRegion->linearAddress.get(); } - // NOTE: Each task gets 16KB of stack. - static const DWORD defaultStackSize = 16384; - if (isRing0()) { // FIXME: This memory is leaked. // But uh, there's also no kernel task termination, so I guess it's not technically leaked... @@ -327,8 +326,9 @@ Task::Task(void (*e)(), const char* n, IPC::Handle h, RingLevel ring) s_tasks->prepend(this); system.nprocess++; - +#ifdef TASK_DEBUG kprintf("Task %u (%s) spawned @ %p\n", m_pid, m_name.characters(), m_tss.eip); +#endif } Task::~Task() @@ -359,7 +359,9 @@ void Task::dumpRegions() void Task::sys$exit(int status) { cli(); +#ifdef TASK_DEBUG kprintf("sys$exit: %s(%u) exit with status %d\n", name().characters(), pid(), status); +#endif setState(Exiting); @@ -473,6 +475,13 @@ bool scheduleNewTask() continue; } } + + if (task->state() == Task::BlockedWait) { + if (!Task::fromPID(task->waitee())) { + task->unblock(); + continue; + } + } } auto* prevHead = s_tasks->head(); @@ -693,6 +702,16 @@ pid_t Task::sys$getpid() return m_pid; } +pid_t Task::sys$waitpid(pid_t waitee) +{ + if (!Task::fromPID(waitee)) + return -1; + m_waitee = waitee; + block(BlockedWait); + yield(); + return m_waitee; +} + bool Task::acceptsMessageFrom(Task& peer) { return !ipc.msg.isValid() && (ipc.src == IPC::Handle::Any || ipc.src == peer.handle()); diff --git a/Kernel/Task.h b/Kernel/Task.h index 06c8dc8212..7427daee80 100644 --- a/Kernel/Task.h +++ b/Kernel/Task.h @@ -37,6 +37,7 @@ public: Terminated = 6, Crashing = 7, Exiting = 8, + BlockedWait = 9, }; enum RingLevel { @@ -97,6 +98,7 @@ public: void sys$sleep(DWORD ticks); void sys$exit(int status); int sys$spawn(const char* path); + pid_t sys$waitpid(pid_t); struct { @@ -116,6 +118,8 @@ public: void didSchedule() { ++m_timesScheduled; } dword timesScheduled() const { return m_timesScheduled; } + pid_t waitee() const { return m_waitee; } + private: friend class MemoryManager; @@ -145,6 +149,7 @@ private: int m_error { 0 }; void* m_kernelStack { nullptr }; dword m_timesScheduled { 0 }; + pid_t m_waitee { -1 }; struct Region { Region(LinearAddress, size_t, RetainPtr&&, String&&); diff --git a/Kernel/_fs_contents b/Kernel/_fs_contents index e74551456e35e00dd6d24e4cef5777a3c55b7928..70277d8a7b6b46678562f84003bee4969fa4821e 100644 GIT binary patch delta 12524 zcmeHN4RF-O72mxiWG^3ZcS%T)kGqgSki?K92@T;xK%kL2kWfc#`ATdkp=ClyE=fm_ zi>3+@X@NsmN7^1!1{}*EHf=*^w1$F~PDQ1o<403Ff>t`T*3?!agQUN=yZ__zH^QL9 zl+N5gv-AG%?Y{lE-S>X)?LTeZGuygn9!iPlGL#zcb-w=C%S)+D>MV`Fg*#f}p5_lY zc8U}(J5$9c!yLml?cin3{`Of6Pj~+gUfj7cYs-kCWtogUIPE2+`}$*{ou!LIwUfi8 zfi%Vf&z~^jmzR)KpxhGj7v*=>7W*8fEFGf1TD=agJ{KzU zQ0Ak26{SL{zgs%}$7z9~dYBSLCNLlKb`=-!?ji9VzdgK5uG}alOK&kB!CBW|CJV{s zOUt-VUfd*H^5Qb?3O(7oSXP$u!ch6Y76fU^9_C^dx=$t)pTyP~z7J!2SOQx#pgx)1 zF@Sfn<%S;v>cL;F;j*z@RxqeT?OU@?ne>5%0zCM!bu$1gwL5AUAZ0p>>A- z%Frrm?`AB^@CyuWG4%U}z5wc>4ijmh@l5@2j@+)K1ESConWg`r_?fI^uM&?aF9bHJvx{q!2%y z<~{}iow6Y)^n5ChOy`*yui-UXoQ&CxA%&?YQR76Jg+k9StX}bsRj_yz8s!uU^)MNQ zo*P3a-ph2K#~VqpX!XpMH8XhT)Q`bLclr!EJq+1slnfNB(^Tk2tB19^6S8RaK*}X` z7+yquv`zhj`bhg3p+Wa%veTLWO?_!%ZU(W8rHh8eJ519tq{GDu<;kEgvvBwRs&3`Bh z%Z|0;*2IR!b>CXm)D-&j+nEs~`{!D*FbE5Tl`GS|!BAK~bL28clq?mm%yAQArG_sz z^|ukl?$;8%k+DWo-)ic282%B%A2fWY;g5p`9oaaqbi^>wa8O4+d=k+-#)^%+jCjmq z4$-lUEhLJ8E2u+2it%P6|{xDNu4! zB!?GZjsm^gj)`3>>cw1#*LYG^7+CeaKw(p$aqX&li)pB74Y^N^lu6@wST?K|)y@En zz=v+K<(un84! zc3TsG96xZxRjDHY-g2LJ%RMxh7Zad4SmHL>OH=!b5o4RwlP-JFdMcfl=)v}4FmkKe zC~yIh!4}xm8Ysjo#+UU|->d1HeFYrF zff9!jkCK2g1SN65uRxTfmBFs)vHb3MHctCppYppYr%~75=h)<`th_^hP%Vo1esaO( z!6n-sCO^Bld2_KJzED)yhM57jy_F(2geL=y;Zepc2!j^9^kXdhm#+O)`@oD z(Drx#?QV3tZPmY*u2{Kz+v>iRee6BeyQ%0ADlf4%+hu83#vI9geUG0Y%uv>(e_ zI?&nQ;A?_q)~~AdAq4V`YcBAS5wEFV?ORvxTN5ZOER=ipi$92_hSqviC+$Go=NiLL zQQTJoQX?M9QNqBptzZjk^Mp8zgA$8jS)Qveg}fZ@XrT}RvfHr z0T%GdgM!648(0+DzykFHz+$2eEKolHEWjVcnh6sWSb#qcK1j|#iHrsn3M}B8Dadh5 zz<@?xPCOLm8J>)t_$s0~j4dY$>#Cput`0oDW=D@Jg9l*KO#=UsssQD@1{8;MZ?OO+iQe-PJeYnIprpVaXhAs|P;SC|6rjx0 zfU;3COl#H`b$5bOYvl@M56DW-%sEPLH=@^X8A9j&aLG6%bO`b^O2ssIE2!*0G za;@n>PQSn9!UYDTF)du#r{E@o0*`3%0ZgScbn?A4_cT*uAx^bM90H=~@d_{=K?co` z!YOM!idd*)OZ^$GPG>V({oN>aO3*Cz6*l!Ox#K~RnX%T0tyN4wROwXHz1P&lp%Z%i z@*OC+H$zOjWfMPSTC1k2wSTL~OD&-w6-{$N#_H(41V_wZ(QfR-?yh?`@Uw9g-!n{| z9t&rXT>r9|CnxIMdeVN;d>tm$+c9AeHlRU{G1@ZV%zhK5aiNaas83#+b$zvwcKv>L)*{gIv+(s zIt$HJ%IyvHoU3%c0a1|>QQ954y>Eh3ATrS+%DO{)`@+sLi0Fi=q}wYmxcKcl^UgR1 zDb88M%quXRp=9QtNxttujY_^}oJ9L*`pQV~C?Wu0Y3Rw^vHQ(}n!N&46r<*=^{Vc!V;|8WD*f)jo%g1YPB24Fx?mk&F{ zTFHkF2Vvuh6U2S78-XWakUrR%xe;i& z6u=!v%^_8z0=QSPsOSLh9htpZOycGy;7z$+b1Go_LpaZtbEg}or zD)TRZG%8R-Zcmy2!odTzI|tAFzpY!_Gyet^it&%+o-HD69L7=k_vMoPAL!`Ip6u^} zu8zL!`F_RV`TiLMvE+rbQ7)J7@73z|d_QcWFH*l;zRy(j^_g7XrDH66u5ZNlT;C-r z#&Wt4V@2iqgd--tx)Y%Q<@%ERcI?wd?9+ukfQo&(VCG}QHU4xFOKoDQO)Ryc)aZIn zZDJo7ksZW7Fj97)?u?Ng9LJH3ePBeQ5&OWXzcJ%HSXV@`4~&=nz!Ry0I%= zeI}ueD^k0p!tAW_nKtRaiGMZ#G@pj48eabB&Kcr EFH0h{K>z>% delta 5989 zcmeHKe^6A{6~1>_;H@I;4{#x(JlN=>t`RgCeiw>qO(wQrY%md9QLv))qh_yB8WKu1um@zuEK_%11nrWxOiJ53)TWA~y8pom->38mXyDlrXnWTTz zj(524yz||2?>+DS`1p2XNB+i+{DVG5&$F?8m_1qj9I=MNV48!zAO{bc=z20uPle@A`*1z5RF!Gw`Jw^eg zRX;*^?<-XVHNA2MP>)vI8|x~lvlbVZRyF$v$3Q2y$RXwY=^dXow^w`kFC)e^{pQG~ z1jgRm_>N0u_p5ArMdh>8Ysyzvtg05R&B_lFR#dFZRwveZ)Ri@r=6nDLX z)a*D8TVSaSU^(q9l6_BinchBzEgR;KX4QsI$H30w*c!v1Abkh>q2b3%-^%I@e>t|% z&dhAH?oVMVcE!#tY=;pLEj!qmX87ZzAI+LY|1RYbv1b+^9Z|DtY2}(V;$Vi7B3`Rj zGVAYW%!)XU$9;xPf;FWuMwa7zA%vNxGDc^W{A{EBF|zpR3bJm-YK-=^M!V1OcN+d1 zhTmrRU9j~gl`%SkH1Ij2VJyCs{8U)eWK2wUB4b4cK8JiHSV|TN%%T2v#=`N=ac$BJ zTWZ)U!yYzl3B}`b;`+{%9Ue6ro;B=d!=5y3BqcV5$t^Xdiu_D|v~AHpo46?W7Ec&e zTe+_Gfit}WXrJQd zf6{(^-EHw;`_iaQ>%X4FPiwY8x1}tA6%Hox%Ub!Mn_tD#sqG!K@|)Tr_z`0Ke#LFs zflxYes+hYULnn)Bpgc<}x#8wTTI&s`?IW~e!B_+;l@hK0hLfMw`UjoKDts&mPM1E) z-(iDeS798d?W%#!fTi-BR`|Iy&W1pW^`mq#elE)G++mw+G+`NK@o2u!ommrsTHqJx zAlrr1kKkQJr9HrYEfr1$)oTfON7`+GkY()*&8e$#1t%0P+Gs9e!D0bLA~ z7H>FOX~fDvf2`JV(>mq~(m#WbN(QQmWIejh=``Pvl{bqCV)Dg9A=wICIx<6L>n8pU^(($>B{}Qt#7#DkL88Q~JnM zXbDiE@HQ*WZT9}IyMo!C#6tgnGMkx>5H^|^jhM_u7EG3I;Iqh2VeDbDI8bx2$6u1k zLW#^Jfv?VFnZudvNu9|S0Hy!Us*p_9t}|JuWU@ZA-D0x0C6lScnCzTnvWo#GyCj+H zis;{=IJLe(tEG52o5kpC=9X-hJ|dfajo2*fEK&-lmIeNCfd4ywTQnlSeSbuLs|Hi} zM&>s*BEK#Eg8WuCBEQ9dL4G?jBENNw$Zt9t%5M^t{ML0lzct_Dw=>8{^4sHFOaCCT zE&9>~vq+2NrNjB>h5sPDw89U6D-u<{Oq=qLjbh~q#VRhB@ieg~!2q3Ra$z7Uy2i7MpKzi&m z$zp>677G(4wa{FnNsvvS2v%pf_yIlg7T&R30r@ovxo2pH{_M#570_VPI*)F2BxnS( zenr!X_uvs0O42$Lf>ug;ybyw}k@QFsFnFdu%tT8_GeI{8X1a{`;F)}Krt1dk7kVv{ z9^(*5v3|4_1HP`)BOM=V!U>V3SP~qG!r&wZkOav;N&>&*0!b8v^nRUs=aDE3?tRdp zN9s*Kc>If19MW6CRkUjF|HTpaU8BXHa6DS#^n`1SrZ5adWtwUz;15C>l0&g&) zWoRIp2-K2>G0)?(U1IzJB`MsB6K06RD(t9NEC1W$hYPqG%ik2q9zLlgkrqH#cTJ}n z28QZV=_fcACZPC^Vlwt=Ui#ITKw?erZ0V?VKG)se zTEIs~wtqZB5xo6$8GnlNtz!41{FLaM#myNULz7r0EixIF{0GP%&)96TSjq)tlNqZr z+N;}b5AlXDjN^;puJE$aQ1IedHh1x(;zBle^Db@fCvLt=r02lt(00T5o!CUqdGUS@ zcZ!Z2Zsk4n?&f_uWX%OMAd+(d-4KtEafm`MuF+KC^D0hpkODHq+!C}Di3@;s<^eH_ z-Gr2j^cN9SOwfK&p2yv$s3@^Lk5A%EynH9GiJjW|@*mZE`*auV(_zoO8|4&t!;QMPQ$&aVyF10#Z{6@b YM>U~_p_);{Q6t(nJRjMx&1Y5q1yXG(lK=n! diff --git a/LibC/unistd.cpp b/LibC/unistd.cpp index 6efa2da1b2..81570ece70 100644 --- a/LibC/unistd.cpp +++ b/LibC/unistd.cpp @@ -35,5 +35,10 @@ int close(int fd) return Syscall::invoke(Syscall::PosixClose, fd); } +pid_t waitpid(pid_t waitee) +{ + return Syscall::invoke(Syscall::PosixWaitpid, waitee); +} + } diff --git a/LibC/unistd.h b/LibC/unistd.h index 2395eadf13..078a90fe0e 100644 --- a/LibC/unistd.h +++ b/LibC/unistd.h @@ -10,6 +10,7 @@ pid_t getpid(); int open(const char* path); ssize_t read(int fd, void* buf, size_t count); int close(int fd); +pid_t waitpid(pid_t); } diff --git a/Userland/sh.cpp b/Userland/sh.cpp index 6ec7a5e42a..68d4cc24b3 100644 --- a/Userland/sh.cpp +++ b/Userland/sh.cpp @@ -18,7 +18,9 @@ static int runcmd(char* cmd) int ret = spawn(buf); if (ret == -1) { printf("spawn failed: %s\n", cmd); + return 1; } + waitpid(ret); return 0; }