Process.cpp 47 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671
  1. #include "types.h"
  2. #include "Process.h"
  3. #include "kmalloc.h"
  4. #include "VGA.h"
  5. #include "StdLib.h"
  6. #include "i386.h"
  7. #include "system.h"
  8. #include <VirtualFileSystem/FileDescriptor.h>
  9. #include <VirtualFileSystem/VirtualFileSystem.h>
  10. #include <ELFLoader/ELFLoader.h>
  11. #include "MemoryManager.h"
  12. #include "errno.h"
  13. #include "i8253.h"
  14. #include "RTC.h"
  15. #include "ProcFileSystem.h"
  16. #include <AK/StdLib.h>
  17. #include <LibC/signal_numbers.h>
  18. //#define DEBUG_IO
  19. //#define TASK_DEBUG
  20. //#define FORK_DEBUG
  21. //#define SCHEDULER_DEBUG
  22. #define COOL_GLOBALS
  23. #define MAX_PROCESS_GIDS 32
  24. static const dword scheduler_time_slice = 5; // *10 = 50ms
  25. #ifdef COOL_GLOBALS
  26. struct CoolGlobals {
  27. dword current_pid;
  28. };
  29. CoolGlobals* g_cool_globals;
  30. #endif
  31. // FIXME: Only do a single validation for accesses that don't span multiple pages.
  32. // FIXME: Some places pass strlen(arg1) as arg2. This doesn't seem entirely perfect..
  33. #define VALIDATE_USER_READ(b, s) \
  34. do { \
  35. LinearAddress laddr((dword)(b)); \
  36. if (!validate_user_read(laddr) || !validate_user_read(laddr.offset((s) - 1))) \
  37. return -EFAULT; \
  38. } while(0)
  39. #define VALIDATE_USER_WRITE(b, s) \
  40. do { \
  41. LinearAddress laddr((dword)(b)); \
  42. if (!validate_user_write(laddr) || !validate_user_write(laddr.offset((s) - 1))) \
  43. return -EFAULT; \
  44. } while(0)
  45. static const DWORD defaultStackSize = 16384;
  46. Process* current;
  47. Process* s_kernelProcess;
  48. static pid_t next_pid;
  49. static InlineLinkedList<Process>* s_processes;
  50. static InlineLinkedList<Process>* s_deadProcesses;
  51. static String* s_hostname;
  52. static String& hostnameStorage(InterruptDisabler&)
  53. {
  54. ASSERT(s_hostname);
  55. return *s_hostname;
  56. }
  57. static String getHostname()
  58. {
  59. InterruptDisabler disabler;
  60. return hostnameStorage(disabler).isolatedCopy();
  61. }
  62. static bool contextSwitch(Process*);
  63. static void redoKernelProcessTSS()
  64. {
  65. if (!s_kernelProcess->selector())
  66. s_kernelProcess->setSelector(gdt_alloc_entry());
  67. auto& tssDescriptor = getGDTEntry(s_kernelProcess->selector());
  68. tssDescriptor.setBase(&s_kernelProcess->tss());
  69. tssDescriptor.setLimit(0xffff);
  70. tssDescriptor.dpl = 0;
  71. tssDescriptor.segment_present = 1;
  72. tssDescriptor.granularity = 1;
  73. tssDescriptor.zero = 0;
  74. tssDescriptor.operation_size = 1;
  75. tssDescriptor.descriptor_type = 0;
  76. tssDescriptor.type = 9;
  77. flushGDT();
  78. }
  79. void Process::prepForIRETToNewProcess()
  80. {
  81. redoKernelProcessTSS();
  82. s_kernelProcess->tss().backlink = current->selector();
  83. loadTaskRegister(s_kernelProcess->selector());
  84. }
  85. static void hlt_loop()
  86. {
  87. for (;;) {
  88. asm volatile("hlt");
  89. }
  90. }
  91. void Process::initialize()
  92. {
  93. #ifdef COOL_GLOBALS
  94. g_cool_globals = (CoolGlobals*)0x1000;
  95. #endif
  96. current = nullptr;
  97. next_pid = 0;
  98. s_processes = new InlineLinkedList<Process>;
  99. s_deadProcesses = new InlineLinkedList<Process>;
  100. s_kernelProcess = Process::createKernelProcess(hlt_loop, "colonel");
  101. s_hostname = new String("birx");
  102. redoKernelProcessTSS();
  103. loadTaskRegister(s_kernelProcess->selector());
  104. }
  105. template<typename Callback>
  106. static void forEachProcess(Callback callback)
  107. {
  108. ASSERT_INTERRUPTS_DISABLED();
  109. for (auto* process = s_processes->head(); process; process = process->next()) {
  110. if (!callback(*process))
  111. break;
  112. }
  113. }
  114. void Process::for_each_in_pgrp(pid_t pgid, Function<void(Process&)> callback)
  115. {
  116. ASSERT_INTERRUPTS_DISABLED();
  117. for (auto* process = s_processes->head(); process; process = process->next()) {
  118. if (process->pgid() == pgid)
  119. callback(*process);
  120. }
  121. }
  122. Vector<Process*> Process::allProcesses()
  123. {
  124. InterruptDisabler disabler;
  125. Vector<Process*> processes;
  126. processes.ensureCapacity(s_processes->sizeSlow());
  127. for (auto* process = s_processes->head(); process; process = process->next())
  128. processes.append(process);
  129. return processes;
  130. }
  131. Region* Process::allocate_region(LinearAddress laddr, size_t size, String&& name, bool is_readable, bool is_writable)
  132. {
  133. // FIXME: This needs sanity checks. What if this overlaps existing regions?
  134. if (laddr.is_null()) {
  135. laddr = m_nextRegion;
  136. m_nextRegion = m_nextRegion.offset(size).offset(PAGE_SIZE);
  137. }
  138. laddr.mask(0xfffff000);
  139. unsigned page_count = ceilDiv(size, PAGE_SIZE);
  140. auto physical_pages = MM.allocate_physical_pages(page_count);
  141. ASSERT(physical_pages.size() == page_count);
  142. m_regions.append(adopt(*new Region(laddr, size, move(physical_pages), move(name), is_readable, is_writable)));
  143. MM.mapRegion(*this, *m_regions.last());
  144. return m_regions.last().ptr();
  145. }
  146. bool Process::deallocate_region(Region& region)
  147. {
  148. InterruptDisabler disabler;
  149. for (size_t i = 0; i < m_regions.size(); ++i) {
  150. if (m_regions[i].ptr() == &region) {
  151. MM.unmapRegion(*this, region);
  152. m_regions.remove(i);
  153. return true;
  154. }
  155. }
  156. return false;
  157. }
  158. Region* Process::regionFromRange(LinearAddress laddr, size_t size)
  159. {
  160. for (auto& region : m_regions) {
  161. if (region->linearAddress == laddr && region->size == size)
  162. return region.ptr();
  163. }
  164. return nullptr;
  165. }
  166. int Process::sys$set_mmap_name(void* addr, size_t size, const char* name)
  167. {
  168. VALIDATE_USER_READ(name, strlen(name));
  169. auto* region = regionFromRange(LinearAddress((dword)addr), size);
  170. if (!region)
  171. return -EINVAL;
  172. region->name = name;
  173. return 0;
  174. }
  175. void* Process::sys$mmap(void* addr, size_t size)
  176. {
  177. InterruptDisabler disabler;
  178. // FIXME: Implement mapping at a client-preferred address.
  179. ASSERT(addr == nullptr);
  180. auto* region = allocate_region(LinearAddress(), size, "mmap");
  181. if (!region)
  182. return (void*)-1;
  183. MM.mapRegion(*this, *region);
  184. return (void*)region->linearAddress.get();
  185. }
  186. int Process::sys$munmap(void* addr, size_t size)
  187. {
  188. InterruptDisabler disabler;
  189. auto* region = regionFromRange(LinearAddress((dword)addr), size);
  190. if (!region)
  191. return -1;
  192. if (!deallocate_region(*region))
  193. return -1;
  194. return 0;
  195. }
  196. int Process::sys$gethostname(char* buffer, size_t size)
  197. {
  198. VALIDATE_USER_WRITE(buffer, size);
  199. auto hostname = getHostname();
  200. if (size < (hostname.length() + 1))
  201. return -ENAMETOOLONG;
  202. memcpy(buffer, hostname.characters(), size);
  203. return 0;
  204. }
  205. Process* Process::fork(RegisterDump& regs)
  206. {
  207. auto* child = new Process(String(m_name), m_uid, m_gid, m_pid, m_ring, m_cwd.copyRef(), m_executable.copyRef(), m_tty, this);
  208. #ifdef FORK_DEBUG
  209. dbgprintf("fork: child=%p\n", child);
  210. #endif
  211. #if 0
  212. // FIXME: An honest fork() would copy these. Needs a Vector copy ctor.
  213. child->m_arguments = m_arguments;
  214. child->m_initialEnvironment = m_initialEnvironment;
  215. #endif
  216. for (auto& region : m_regions) {
  217. #ifdef FORK_DEBUG
  218. dbgprintf("fork: cloning Region{%p}\n", region.ptr());
  219. #endif
  220. auto cloned_region = region->clone();
  221. child->m_regions.append(move(cloned_region));
  222. MM.mapRegion(*child, *child->m_regions.last());
  223. }
  224. child->m_tss.eax = 0; // fork() returns 0 in the child :^)
  225. child->m_tss.ebx = regs.ebx;
  226. child->m_tss.ecx = regs.ecx;
  227. child->m_tss.edx = regs.edx;
  228. child->m_tss.ebp = regs.ebp;
  229. child->m_tss.esp = regs.esp_if_crossRing;
  230. child->m_tss.esi = regs.esi;
  231. child->m_tss.edi = regs.edi;
  232. child->m_tss.eflags = regs.eflags;
  233. child->m_tss.eip = regs.eip;
  234. child->m_tss.cs = regs.cs;
  235. child->m_tss.ds = regs.ds;
  236. child->m_tss.es = regs.es;
  237. child->m_tss.fs = regs.fs;
  238. child->m_tss.gs = regs.gs;
  239. child->m_tss.ss = regs.ss_if_crossRing;
  240. #ifdef FORK_DEBUG
  241. dbgprintf("fork: child will begin executing at %w:%x with stack %w:%x\n", child->m_tss.cs, child->m_tss.eip, child->m_tss.ss, child->m_tss.esp);
  242. #endif
  243. ProcFileSystem::the().addProcess(*child);
  244. s_processes->prepend(child);
  245. system.nprocess++;
  246. #ifdef TASK_DEBUG
  247. kprintf("Process %u (%s) forked from %u @ %p\n", child->pid(), child->name().characters(), m_pid, child->m_tss.eip);
  248. #endif
  249. return child;
  250. }
  251. pid_t Process::sys$fork(RegisterDump& regs)
  252. {
  253. auto* child = fork(regs);
  254. ASSERT(child);
  255. return child->pid();
  256. }
  257. int Process::exec(const String& path, Vector<String>&& arguments, Vector<String>&& environment)
  258. {
  259. auto parts = path.split('/');
  260. if (parts.isEmpty())
  261. return -ENOENT;
  262. int error;
  263. auto descriptor = VirtualFileSystem::the().open(path, error, 0, m_cwd ? m_cwd->inode : InodeIdentifier());
  264. if (!descriptor) {
  265. ASSERT(error != 0);
  266. return error;
  267. }
  268. if (!descriptor->metadata().mayExecute(m_euid, m_gids))
  269. return -EACCES;
  270. auto elfData = descriptor->readEntireFile();
  271. if (!elfData)
  272. return -EIO; // FIXME: Get a more detailed error from VFS.
  273. dword entry_eip = 0;
  274. PageDirectory* old_page_directory;
  275. PageDirectory* new_page_directory;
  276. {
  277. InterruptDisabler disabler;
  278. // Okay, here comes the sleight of hand, pay close attention..
  279. auto old_regions = move(m_regions);
  280. old_page_directory = m_page_directory;
  281. new_page_directory = reinterpret_cast<PageDirectory*>(kmalloc_page_aligned(sizeof(PageDirectory)));
  282. MM.populate_page_directory(*new_page_directory);
  283. m_page_directory = new_page_directory;
  284. MM.enter_process_paging_scope(*this);
  285. ELFLoader loader(move(elfData));
  286. loader.alloc_section_hook = [&] (LinearAddress laddr, size_t size, size_t alignment, bool is_readable, bool is_writable, const String& name) {
  287. ASSERT(size);
  288. size = ((size / 4096) + 1) * 4096; // FIXME: Use ceil_div?
  289. (void) allocate_region(laddr, size, String(name), is_readable, is_writable);
  290. return laddr.asPtr();
  291. };
  292. bool success = loader.load();
  293. if (!success) {
  294. m_page_directory = old_page_directory;
  295. MM.enter_process_paging_scope(*this);
  296. MM.release_page_directory(*new_page_directory);
  297. m_regions = move(old_regions);
  298. kprintf("sys$execve: Failure loading %s\n", path.characters());
  299. return -ENOEXEC;
  300. }
  301. entry_eip = (dword)loader.symbol_ptr("_start");
  302. if (!entry_eip) {
  303. m_page_directory = old_page_directory;
  304. MM.enter_process_paging_scope(*this);
  305. MM.release_page_directory(*new_page_directory);
  306. m_regions = move(old_regions);
  307. return -ENOEXEC;
  308. }
  309. }
  310. InterruptDisabler disabler;
  311. if (current == this)
  312. loadTaskRegister(s_kernelProcess->selector());
  313. m_name = parts.takeLast();
  314. dword old_esp0 = m_tss.esp0;
  315. memset(&m_tss, 0, sizeof(m_tss));
  316. m_tss.eflags = 0x0202;
  317. m_tss.eip = entry_eip;
  318. m_tss.cs = 0x1b;
  319. m_tss.ds = 0x23;
  320. m_tss.es = 0x23;
  321. m_tss.fs = 0x23;
  322. m_tss.gs = 0x23;
  323. m_tss.ss = 0x23;
  324. m_tss.cr3 = (dword)m_page_directory;
  325. auto* stack_region = allocate_region(LinearAddress(), defaultStackSize, "stack");
  326. ASSERT(stack_region);
  327. m_stackTop3 = stack_region->linearAddress.offset(defaultStackSize).get() & 0xfffffff8;
  328. m_tss.esp = m_stackTop3;
  329. m_tss.ss0 = 0x10;
  330. m_tss.esp0 = old_esp0;
  331. m_tss.ss2 = m_pid;
  332. MM.release_page_directory(*old_page_directory);
  333. m_executable = descriptor->vnode();
  334. m_arguments = move(arguments);
  335. m_initialEnvironment = move(environment);
  336. #ifdef TASK_DEBUG
  337. kprintf("Process %u (%s) exec'd %s @ %p\n", pid(), name().characters(), filename, m_tss.eip);
  338. #endif
  339. if (current == this)
  340. sched_yield();
  341. return 0;
  342. }
  343. int Process::sys$execve(const char* filename, const char** argv, const char** envp)
  344. {
  345. VALIDATE_USER_READ(filename, strlen(filename));
  346. if (argv) {
  347. for (size_t i = 0; argv[i]; ++i) {
  348. VALIDATE_USER_READ(argv[i], strlen(argv[i]));
  349. }
  350. }
  351. if (envp) {
  352. for (size_t i = 0; envp[i]; ++i) {
  353. VALIDATE_USER_READ(envp[i], strlen(envp[i]));
  354. }
  355. }
  356. String path(filename);
  357. auto parts = path.split('/');
  358. Vector<String> arguments;
  359. if (argv) {
  360. for (size_t i = 0; argv[i]; ++i) {
  361. arguments.append(argv[i]);
  362. }
  363. } else {
  364. arguments.append(parts.last());
  365. }
  366. Vector<String> environment;
  367. if (envp) {
  368. for (size_t i = 0; envp[i]; ++i) {
  369. environment.append(envp[i]);
  370. }
  371. }
  372. int rc = exec(path, move(arguments), move(environment));
  373. ASSERT(rc < 0);
  374. return rc;
  375. }
  376. pid_t Process::sys$spawn(const char* filename, const char** argv, const char** envp)
  377. {
  378. VALIDATE_USER_READ(filename, strlen(filename));
  379. if (argv) {
  380. for (size_t i = 0; argv[i]; ++i) {
  381. VALIDATE_USER_READ(argv[i], strlen(argv[i]));
  382. }
  383. }
  384. if (envp) {
  385. for (size_t i = 0; envp[i]; ++i) {
  386. VALIDATE_USER_READ(envp[i], strlen(envp[i]));
  387. }
  388. }
  389. String path(filename);
  390. auto parts = path.split('/');
  391. Vector<String> arguments;
  392. if (argv) {
  393. for (size_t i = 0; argv[i]; ++i) {
  394. arguments.append(argv[i]);
  395. }
  396. } else {
  397. arguments.append(parts.last());
  398. }
  399. Vector<String> environment;
  400. if (envp) {
  401. for (size_t i = 0; envp[i]; ++i) {
  402. environment.append(envp[i]);
  403. }
  404. }
  405. int error;
  406. auto* child = create_user_process(path, m_uid, m_gid, m_pid, error, move(arguments), move(environment), m_tty);
  407. if (child)
  408. return child->pid();
  409. return error;
  410. }
  411. Process* Process::create_user_process(const String& path, uid_t uid, gid_t gid, pid_t parent_pid, int& error, Vector<String>&& arguments, Vector<String>&& environment, TTY* tty)
  412. {
  413. // FIXME: Don't split() the path twice (sys$spawn also does it...)
  414. auto parts = path.split('/');
  415. if (arguments.isEmpty()) {
  416. arguments.append(parts.last());
  417. }
  418. RetainPtr<VirtualFileSystem::Node> cwd;
  419. {
  420. InterruptDisabler disabler;
  421. if (auto* parent = Process::fromPID(parent_pid))
  422. cwd = parent->m_cwd.copyRef();
  423. }
  424. if (!cwd)
  425. cwd = VirtualFileSystem::the().root();
  426. auto* process = new Process(parts.takeLast(), uid, gid, parent_pid, Ring3, move(cwd), nullptr, tty);
  427. error = process->exec(path, move(arguments), move(environment));
  428. if (error != 0)
  429. return nullptr;
  430. ProcFileSystem::the().addProcess(*process);
  431. s_processes->prepend(process);
  432. system.nprocess++;
  433. #ifdef TASK_DEBUG
  434. kprintf("Process %u (%s) spawned @ %p\n", process->pid(), process->name().characters(), process->m_tss.eip);
  435. #endif
  436. error = 0;
  437. return process;
  438. }
  439. int Process::sys$get_environment(char*** environ)
  440. {
  441. auto* region = allocate_region(LinearAddress(), PAGE_SIZE, "environ");
  442. if (!region)
  443. return -ENOMEM;
  444. MM.mapRegion(*this, *region);
  445. char* envpage = (char*)region->linearAddress.get();
  446. *environ = (char**)envpage;
  447. char* bufptr = envpage + (sizeof(char*) * (m_initialEnvironment.size() + 1));
  448. for (size_t i = 0; i < m_initialEnvironment.size(); ++i) {
  449. (*environ)[i] = bufptr;
  450. memcpy(bufptr, m_initialEnvironment[i].characters(), m_initialEnvironment[i].length());
  451. bufptr += m_initialEnvironment[i].length();
  452. *(bufptr++) = '\0';
  453. }
  454. (*environ)[m_initialEnvironment.size()] = nullptr;
  455. return 0;
  456. }
  457. int Process::sys$get_arguments(int* argc, char*** argv)
  458. {
  459. auto* region = allocate_region(LinearAddress(), PAGE_SIZE, "argv");
  460. if (!region)
  461. return -ENOMEM;
  462. MM.mapRegion(*this, *region);
  463. char* argpage = (char*)region->linearAddress.get();
  464. *argc = m_arguments.size();
  465. *argv = (char**)argpage;
  466. char* bufptr = argpage + (sizeof(char*) * m_arguments.size());
  467. for (size_t i = 0; i < m_arguments.size(); ++i) {
  468. (*argv)[i] = bufptr;
  469. memcpy(bufptr, m_arguments[i].characters(), m_arguments[i].length());
  470. bufptr += m_arguments[i].length();
  471. *(bufptr++) = '\0';
  472. }
  473. return 0;
  474. }
  475. Process* Process::createKernelProcess(void (*e)(), String&& name)
  476. {
  477. auto* process = new Process(move(name), (uid_t)0, (gid_t)0, (pid_t)0, Ring0);
  478. process->m_tss.eip = (dword)e;
  479. if (process->pid() != 0) {
  480. InterruptDisabler disabler;
  481. s_processes->prepend(process);
  482. system.nprocess++;
  483. ProcFileSystem::the().addProcess(*process);
  484. #ifdef TASK_DEBUG
  485. kprintf("Kernel process %u (%s) spawned @ %p\n", process->pid(), process->name().characters(), process->m_tss.eip);
  486. #endif
  487. }
  488. return process;
  489. }
  490. Process::Process(String&& name, uid_t uid, gid_t gid, pid_t ppid, RingLevel ring, RetainPtr<VirtualFileSystem::Node>&& cwd, RetainPtr<VirtualFileSystem::Node>&& executable, TTY* tty, Process* fork_parent)
  491. : m_name(move(name))
  492. , m_pid(next_pid++) // FIXME: RACE: This variable looks racy!
  493. , m_uid(uid)
  494. , m_gid(gid)
  495. , m_euid(uid)
  496. , m_egid(gid)
  497. , m_state(Runnable)
  498. , m_ring(ring)
  499. , m_cwd(move(cwd))
  500. , m_executable(move(executable))
  501. , m_tty(tty)
  502. , m_ppid(ppid)
  503. {
  504. m_gids.set(m_gid);
  505. if (fork_parent) {
  506. m_sid = fork_parent->m_sid;
  507. m_pgid = fork_parent->m_pgid;
  508. } else {
  509. // FIXME: Use a ProcessHandle? Presumably we're executing *IN* the parent right now though..
  510. InterruptDisabler disabler;
  511. if (auto* parent = Process::fromPID(m_ppid)) {
  512. m_sid = parent->m_sid;
  513. m_pgid = parent->m_pgid;
  514. }
  515. }
  516. m_page_directory = (PageDirectory*)kmalloc_page_aligned(sizeof(PageDirectory));
  517. MM.populate_page_directory(*m_page_directory);
  518. if (fork_parent) {
  519. m_file_descriptors.resize(fork_parent->m_file_descriptors.size());
  520. for (size_t i = 0; i < fork_parent->m_file_descriptors.size(); ++i) {
  521. if (!fork_parent->m_file_descriptors[i])
  522. continue;
  523. #ifdef FORK_DEBUG
  524. dbgprintf("fork: cloning fd %u... (%p) istty? %um\n", i, fork_parent->m_file_descriptors[i].ptr(), fork_parent->m_file_descriptors[i]->isTTY());
  525. #endif
  526. m_file_descriptors[i] = fork_parent->m_file_descriptors[i]->clone();
  527. }
  528. } else {
  529. m_file_descriptors.resize(m_max_open_file_descriptors);
  530. if (tty) {
  531. m_file_descriptors[0] = tty->open(O_RDONLY);
  532. m_file_descriptors[1] = tty->open(O_WRONLY);
  533. m_file_descriptors[2] = tty->open(O_WRONLY);
  534. }
  535. }
  536. if (fork_parent)
  537. m_nextRegion = fork_parent->m_nextRegion;
  538. else
  539. m_nextRegion = LinearAddress(0x10000000);
  540. if (fork_parent) {
  541. memcpy(&m_tss, &fork_parent->m_tss, sizeof(m_tss));
  542. } else {
  543. memset(&m_tss, 0, sizeof(m_tss));
  544. // Only IF is set when a process boots.
  545. m_tss.eflags = 0x0202;
  546. word cs, ds, ss;
  547. if (isRing0()) {
  548. cs = 0x08;
  549. ds = 0x10;
  550. ss = 0x10;
  551. } else {
  552. cs = 0x1b;
  553. ds = 0x23;
  554. ss = 0x23;
  555. }
  556. m_tss.ds = ds;
  557. m_tss.es = ds;
  558. m_tss.fs = ds;
  559. m_tss.gs = ds;
  560. m_tss.ss = ss;
  561. m_tss.cs = cs;
  562. }
  563. m_tss.cr3 = (dword)m_page_directory;
  564. if (isRing0()) {
  565. // FIXME: This memory is leaked.
  566. // But uh, there's also no kernel process termination, so I guess it's not technically leaked...
  567. dword stackBottom = (dword)kmalloc_eternal(defaultStackSize);
  568. m_stackTop0 = (stackBottom + defaultStackSize) & 0xffffff8;
  569. m_tss.esp = m_stackTop0;
  570. } else {
  571. if (fork_parent) {
  572. m_stackTop3 = fork_parent->m_stackTop3;
  573. } else {
  574. auto* region = allocate_region(LinearAddress(), defaultStackSize, "stack");
  575. ASSERT(region);
  576. m_stackTop3 = region->linearAddress.offset(defaultStackSize).get() & 0xfffffff8;
  577. m_tss.esp = m_stackTop3;
  578. }
  579. }
  580. if (isRing3()) {
  581. // Ring3 processes need a separate stack for Ring0.
  582. m_kernelStack = kmalloc(defaultStackSize);
  583. m_stackTop0 = ((DWORD)m_kernelStack + defaultStackSize) & 0xffffff8;
  584. m_tss.ss0 = 0x10;
  585. m_tss.esp0 = m_stackTop0;
  586. }
  587. // HACK: Ring2 SS in the TSS is the current PID.
  588. m_tss.ss2 = m_pid;
  589. m_farPtr.offset = 0x98765432;
  590. }
  591. Process::~Process()
  592. {
  593. InterruptDisabler disabler;
  594. ProcFileSystem::the().removeProcess(*this);
  595. system.nprocess--;
  596. gdt_free_entry(selector());
  597. if (m_kernelStack) {
  598. kfree(m_kernelStack);
  599. m_kernelStack = nullptr;
  600. }
  601. MM.release_page_directory(*m_page_directory);
  602. }
  603. void Process::dumpRegions()
  604. {
  605. kprintf("Process %s(%u) regions:\n", name().characters(), pid());
  606. kprintf("BEGIN END SIZE NAME\n");
  607. for (auto& region : m_regions) {
  608. kprintf("%x -- %x %x %s\n",
  609. region->linearAddress.get(),
  610. region->linearAddress.offset(region->size - 1).get(),
  611. region->size,
  612. region->name.characters());
  613. }
  614. }
  615. void Process::sys$exit(int status)
  616. {
  617. cli();
  618. #ifdef TASK_DEBUG
  619. kprintf("sys$exit: %s(%u) exit with status %d\n", name().characters(), pid(), status);
  620. #endif
  621. set_state(Dead);
  622. m_termination_status = status;
  623. m_termination_signal = 0;
  624. if (!scheduleNewProcess()) {
  625. kprintf("Process::sys$exit: Failed to schedule a new process :(\n");
  626. HANG;
  627. }
  628. switchNow();
  629. }
  630. void Process::terminate_due_to_signal(byte signal)
  631. {
  632. ASSERT_INTERRUPTS_DISABLED();
  633. ASSERT(signal < 32);
  634. dbgprintf("terminate_due_to_signal %s(%u) <- %u\n", name().characters(), pid(), signal);
  635. m_termination_status = 0;
  636. m_termination_signal = signal;
  637. set_state(Dead);
  638. }
  639. void Process::send_signal(byte signal, Process* sender)
  640. {
  641. ASSERT_INTERRUPTS_DISABLED();
  642. ASSERT(signal < 32);
  643. m_pending_signals |= 1 << signal;
  644. if (sender)
  645. dbgprintf("signal: %s(%u) sent %d to %s(%u)\n", sender->name().characters(), sender->pid(), signal, name().characters(), pid());
  646. else
  647. dbgprintf("signal: kernel sent %d to %s(%u)\n", signal, name().characters(), pid());
  648. }
  649. bool Process::has_unmasked_pending_signals() const
  650. {
  651. return m_pending_signals & ~m_signal_mask;
  652. }
  653. void Process::dispatch_one_pending_signal()
  654. {
  655. ASSERT_INTERRUPTS_DISABLED();
  656. dword signal_candidates = m_pending_signals & ~m_signal_mask;
  657. ASSERT(signal_candidates);
  658. byte signal = 0;
  659. for (; signal < 32; ++signal) {
  660. if (signal_candidates & (1 << signal)) {
  661. break;
  662. }
  663. }
  664. dispatch_signal(signal);
  665. }
  666. void Process::dispatch_signal(byte signal)
  667. {
  668. ASSERT_INTERRUPTS_DISABLED();
  669. ASSERT(signal < 32);
  670. dbgprintf("dispatch_signal %s(%u) <- %u\n", name().characters(), pid(), signal);
  671. auto& action = m_signal_action_data[signal];
  672. // FIXME: Implement SA_SIGINFO signal handlers.
  673. ASSERT(!(action.flags & SA_SIGINFO));
  674. auto handler_laddr = action.handler_or_sigaction;
  675. if (handler_laddr.is_null()) {
  676. // FIXME: Is termination really always the appropriate action?
  677. return terminate_due_to_signal(signal);
  678. }
  679. word ret_cs = m_tss.cs;
  680. dword ret_eip = m_tss.eip;
  681. dword ret_eflags = m_tss.eflags;
  682. if ((ret_cs & 3) == 0) {
  683. // FIXME: Handle send_signal to process currently in kernel code.
  684. kprintf("Boo! dispatch_signal in %s(%u) with return to %w:%x\n", name().characters(), pid(), ret_cs, ret_eip);
  685. ASSERT_NOT_REACHED();
  686. }
  687. ProcessPagingScope pagingScope(*this);
  688. dword old_esp = m_tss.esp;
  689. push_value_on_stack(ret_eip);
  690. push_value_on_stack(ret_eflags);
  691. push_value_on_stack(m_tss.eax);
  692. push_value_on_stack(m_tss.ecx);
  693. push_value_on_stack(m_tss.edx);
  694. push_value_on_stack(m_tss.ebx);
  695. push_value_on_stack(old_esp);
  696. push_value_on_stack(m_tss.ebp);
  697. push_value_on_stack(m_tss.esi);
  698. push_value_on_stack(m_tss.edi);
  699. m_tss.eax = (dword)signal;
  700. m_tss.cs = 0x1b;
  701. m_tss.eip = handler_laddr.get();
  702. if (m_return_from_signal_trampoline.is_null()) {
  703. // FIXME: This should be a global trampoline shared by all processes, not one created per process!
  704. // FIXME: Remap as read-only after setup.
  705. auto* region = allocate_region(LinearAddress(), PAGE_SIZE, "signal_trampoline", true, true);
  706. m_return_from_signal_trampoline = region->linearAddress;
  707. byte* code_ptr = m_return_from_signal_trampoline.asPtr();
  708. *code_ptr++ = 0x61; // popa
  709. *code_ptr++ = 0x9d; // popf
  710. *code_ptr++ = 0xc3; // ret
  711. *code_ptr++ = 0x0f; // ud2
  712. *code_ptr++ = 0x0b;
  713. // FIXME: For !SA_NODEFER, maybe we could do something like emitting an int 0x80 syscall here that
  714. // unmasks the signal so it can be received again? I guess then I would need one trampoline
  715. // per signal number if it's hard-coded, but it's just a few bytes per each.
  716. }
  717. push_value_on_stack(m_return_from_signal_trampoline.get());
  718. m_pending_signals &= ~(1 << signal);
  719. dbgprintf("signal: Okay, %s(%u) has been primed\n", name().characters(), pid());
  720. }
  721. void Process::push_value_on_stack(dword value)
  722. {
  723. m_tss.esp -= 4;
  724. dword* stack_ptr = (dword*)m_tss.esp;
  725. *stack_ptr = value;
  726. }
  727. void Process::crash()
  728. {
  729. ASSERT_INTERRUPTS_DISABLED();
  730. ASSERT(state() != Dead);
  731. m_termination_signal = SIGSEGV;
  732. set_state(Dead);
  733. dumpRegions();
  734. if (!scheduleNewProcess()) {
  735. kprintf("Process::crash: Failed to schedule a new process :(\n");
  736. HANG;
  737. }
  738. switchNow();
  739. }
  740. void Process::doHouseKeeping()
  741. {
  742. if (s_deadProcesses->isEmpty())
  743. return;
  744. InterruptDisabler disabler;
  745. Process* next = nullptr;
  746. for (auto* deadProcess = s_deadProcesses->head(); deadProcess; deadProcess = next) {
  747. next = deadProcess->next();
  748. delete deadProcess;
  749. }
  750. s_deadProcesses->clear();
  751. }
  752. int sched_yield()
  753. {
  754. if (!current) {
  755. kprintf( "PANIC: yield() with !current" );
  756. HANG;
  757. }
  758. //kprintf("%s<%u> yield()\n", current->name().characters(), current->pid());
  759. InterruptDisabler disabler;
  760. if (!scheduleNewProcess())
  761. return 1;
  762. //kprintf("yield() jumping to new process: %x (%s)\n", current->farPtr().selector, current->name().characters());
  763. switchNow();
  764. return 0;
  765. }
  766. void switchNow()
  767. {
  768. Descriptor& descriptor = getGDTEntry(current->selector());
  769. descriptor.type = 9;
  770. flushGDT();
  771. asm("sti\n"
  772. "ljmp *(%%eax)\n"
  773. ::"a"(&current->farPtr())
  774. );
  775. }
  776. template<typename Callback>
  777. static void for_each_process_in_state(Process::State state, Callback callback)
  778. {
  779. ASSERT_INTERRUPTS_DISABLED();
  780. for (auto* process = s_processes->head(); process;) {
  781. auto* next_process = process->next();
  782. if (process->state() == state)
  783. callback(*process);
  784. process = next_process;
  785. }
  786. }
  787. template<typename Callback>
  788. static void for_each_process_not_in_state(Process::State state, Callback callback)
  789. {
  790. ASSERT_INTERRUPTS_DISABLED();
  791. for (auto* process = s_processes->head(); process;) {
  792. auto* next_process = process->next();
  793. if (process->state() != state)
  794. callback(*process);
  795. process = next_process;
  796. }
  797. }
  798. bool scheduleNewProcess()
  799. {
  800. ASSERT_INTERRUPTS_DISABLED();
  801. if (!current) {
  802. // XXX: The first ever context_switch() goes to the idle process.
  803. // This to setup a reliable place we can return to.
  804. return contextSwitch(Process::kernelProcess());
  805. }
  806. // Check and unblock processes whose wait conditions have been met.
  807. for (auto* process = s_processes->head(); process; process = process->next()) {
  808. if (process->state() == Process::BlockedSleep) {
  809. if (process->wakeupTime() <= system.uptime)
  810. process->unblock();
  811. continue;
  812. }
  813. if (process->state() == Process::BlockedWait) {
  814. auto* waitee = Process::fromPID(process->waitee());
  815. if (!waitee) {
  816. kprintf("waitee %u of %s(%u) reaped before I could wait?\n", process->waitee(), process->name().characters(), process->pid());
  817. ASSERT_NOT_REACHED();
  818. }
  819. if (waitee->state() == Process::Dead) {
  820. process->m_waitee_status = (waitee->m_termination_status << 8) | waitee->m_termination_signal;
  821. process->unblock();
  822. waitee->set_state(Process::Forgiven);
  823. }
  824. continue;
  825. }
  826. if (process->state() == Process::BlockedRead) {
  827. ASSERT(process->m_fdBlockedOnRead != -1);
  828. if (process->m_file_descriptors[process->m_fdBlockedOnRead]->hasDataAvailableForRead())
  829. process->unblock();
  830. continue;
  831. }
  832. }
  833. // Forgive dead orphans.
  834. // FIXME: Does this really make sense?
  835. for_each_process_in_state(Process::Dead, [] (auto& process) {
  836. if (!Process::fromPID(process.ppid()))
  837. process.set_state(Process::Forgiven);
  838. });
  839. // Clean up forgiven processes.
  840. // FIXME: Do we really need this to be a separate pass over the process list?
  841. for_each_process_in_state(Process::Forgiven, [] (auto& process) {
  842. s_processes->remove(&process);
  843. s_deadProcesses->append(&process);
  844. });
  845. // Dispatch any pending signals.
  846. // FIXME: Do we really need this to be a separate pass over the process list?
  847. for_each_process_not_in_state(Process::Dead, [] (auto& process) {
  848. if (!process.has_unmasked_pending_signals())
  849. return;
  850. process.dispatch_one_pending_signal();
  851. });
  852. #ifdef SCHEDULER_DEBUG
  853. dbgprintf("Scheduler choices:\n");
  854. for (auto* process = s_processes->head(); process; process = process->next()) {
  855. //if (process->state() == Process::BlockedWait || process->state() == Process::BlockedSleep)
  856. // continue;
  857. dbgprintf("% 12s %s(%u) @ %w:%x\n", toString(process->state()), process->name().characters(), process->pid(), process->tss().cs, process->tss().eip);
  858. }
  859. #endif
  860. auto* prevHead = s_processes->head();
  861. for (;;) {
  862. // Move head to tail.
  863. s_processes->append(s_processes->removeHead());
  864. auto* process = s_processes->head();
  865. if (process->state() == Process::Runnable || process->state() == Process::Running) {
  866. #ifdef SCHEDULER_DEBUG
  867. dbgprintf("switch to %s(%u) (%p vs %p)\n", process->name().characters(), process->pid(), process, current);
  868. #endif
  869. return contextSwitch(process);
  870. }
  871. if (process == prevHead) {
  872. // Back at process_head, nothing wants to run.
  873. kprintf("Nothing wants to run!\n");
  874. kprintf("PID OWNER STATE NSCHED NAME\n");
  875. for (auto* process = s_processes->head(); process; process = process->next()) {
  876. kprintf("%w %w:%w %b %w %s\n",
  877. process->pid(),
  878. process->uid(),
  879. process->gid(),
  880. process->state(),
  881. process->timesScheduled(),
  882. process->name().characters());
  883. }
  884. kprintf("Switch to kernel process @ %w:%x\n", s_kernelProcess->tss().cs, s_kernelProcess->tss().eip);
  885. return contextSwitch(Process::kernelProcess());
  886. }
  887. }
  888. }
  889. static bool contextSwitch(Process* t)
  890. {
  891. t->setTicksLeft(scheduler_time_slice);
  892. t->didSchedule();
  893. if (current == t)
  894. return false;
  895. #ifdef SCHEDULER_DEBUG
  896. // Some sanity checking to force a crash earlier.
  897. auto csRPL = t->tss().cs & 3;
  898. auto ssRPL = t->tss().ss & 3;
  899. if (csRPL != ssRPL) {
  900. kprintf("Fuckup! Switching from %s(%u) to %s(%u) has RPL mismatch\n",
  901. current->name().characters(), current->pid(),
  902. t->name().characters(), t->pid()
  903. );
  904. kprintf("code: %w:%x\n", t->tss().cs, t->tss().eip);
  905. kprintf(" stk: %w:%x\n", t->tss().ss, t->tss().esp);
  906. ASSERT(csRPL == ssRPL);
  907. }
  908. #endif
  909. if (current) {
  910. // If the last process hasn't blocked (still marked as running),
  911. // mark it as runnable for the next round.
  912. if (current->state() == Process::Running)
  913. current->set_state(Process::Runnable);
  914. }
  915. current = t;
  916. t->set_state(Process::Running);
  917. #ifdef COOL_GLOBALS
  918. g_cool_globals->current_pid = t->pid();
  919. #endif
  920. if (!t->selector()) {
  921. t->setSelector(gdt_alloc_entry());
  922. auto& descriptor = getGDTEntry(t->selector());
  923. descriptor.setBase(&t->tss());
  924. descriptor.setLimit(0xffff);
  925. descriptor.dpl = 0;
  926. descriptor.segment_present = 1;
  927. descriptor.granularity = 1;
  928. descriptor.zero = 0;
  929. descriptor.operation_size = 1;
  930. descriptor.descriptor_type = 0;
  931. }
  932. auto& descriptor = getGDTEntry(t->selector());
  933. descriptor.type = 11; // Busy TSS
  934. flushGDT();
  935. return true;
  936. }
  937. Process* Process::fromPID(pid_t pid)
  938. {
  939. ASSERT_INTERRUPTS_DISABLED();
  940. for (auto* process = s_processes->head(); process; process = process->next()) {
  941. if (process->pid() == pid)
  942. return process;
  943. }
  944. return nullptr;
  945. }
  946. FileDescriptor* Process::file_descriptor(int fd)
  947. {
  948. if (fd < 0)
  949. return nullptr;
  950. if ((size_t)fd < m_file_descriptors.size())
  951. return m_file_descriptors[fd].ptr();
  952. return nullptr;
  953. }
  954. const FileDescriptor* Process::file_descriptor(int fd) const
  955. {
  956. if (fd < 0)
  957. return nullptr;
  958. if ((size_t)fd < m_file_descriptors.size())
  959. return m_file_descriptors[fd].ptr();
  960. return nullptr;
  961. }
  962. ssize_t Process::sys$get_dir_entries(int fd, void* buffer, size_t size)
  963. {
  964. VALIDATE_USER_WRITE(buffer, size);
  965. auto* descriptor = file_descriptor(fd);
  966. if (!descriptor)
  967. return -EBADF;
  968. return descriptor->get_dir_entries((byte*)buffer, size);
  969. }
  970. int Process::sys$lseek(int fd, off_t offset, int whence)
  971. {
  972. auto* descriptor = file_descriptor(fd);
  973. if (!descriptor)
  974. return -EBADF;
  975. return descriptor->seek(offset, whence);
  976. }
  977. int Process::sys$ttyname_r(int fd, char* buffer, size_t size)
  978. {
  979. VALIDATE_USER_WRITE(buffer, size);
  980. auto* descriptor = file_descriptor(fd);
  981. if (!descriptor)
  982. return -EBADF;
  983. if (!descriptor->isTTY())
  984. return -ENOTTY;
  985. auto ttyName = descriptor->tty()->ttyName();
  986. if (size < ttyName.length() + 1)
  987. return -ERANGE;
  988. strcpy(buffer, ttyName.characters());
  989. return 0;
  990. }
  991. ssize_t Process::sys$write(int fd, const void* data, size_t size)
  992. {
  993. VALIDATE_USER_READ(data, size);
  994. #ifdef DEBUG_IO
  995. kprintf("Process::sys$write: called(%d, %p, %u)\n", fd, data, size);
  996. #endif
  997. auto* descriptor = file_descriptor(fd);
  998. #ifdef DEBUG_IO
  999. kprintf("Process::sys$write: handle=%p\n", descriptor);
  1000. #endif
  1001. if (!descriptor)
  1002. return -EBADF;
  1003. auto nwritten = descriptor->write((const byte*)data, size);
  1004. #ifdef DEBUG_IO
  1005. kprintf("Process::sys$write: nwritten=%u\n", nwritten);
  1006. #endif
  1007. return nwritten;
  1008. }
  1009. ssize_t Process::sys$read(int fd, void* outbuf, size_t nread)
  1010. {
  1011. VALIDATE_USER_WRITE(outbuf, nread);
  1012. #ifdef DEBUG_IO
  1013. kprintf("Process::sys$read: called(%d, %p, %u)\n", fd, outbuf, nread);
  1014. #endif
  1015. auto* descriptor = file_descriptor(fd);
  1016. #ifdef DEBUG_IO
  1017. kprintf("Process::sys$read: handle=%p\n", descriptor);
  1018. #endif
  1019. if (!descriptor)
  1020. return -EBADF;
  1021. if (descriptor->isBlocking()) {
  1022. if (!descriptor->hasDataAvailableForRead()) {
  1023. m_fdBlockedOnRead = fd;
  1024. block(BlockedRead);
  1025. sched_yield();
  1026. }
  1027. }
  1028. nread = descriptor->read((byte*)outbuf, nread);
  1029. #ifdef DEBUG_IO
  1030. kprintf("Process::sys$read: nread=%u\n", nread);
  1031. #endif
  1032. return nread;
  1033. }
  1034. int Process::sys$close(int fd)
  1035. {
  1036. auto* descriptor = file_descriptor(fd);
  1037. if (!descriptor)
  1038. return -EBADF;
  1039. int rc = descriptor->close();
  1040. m_file_descriptors[fd] = nullptr;
  1041. return rc;
  1042. }
  1043. int Process::sys$lstat(const char* path, Unix::stat* statbuf)
  1044. {
  1045. VALIDATE_USER_WRITE(statbuf, sizeof(Unix::stat));
  1046. int error;
  1047. auto descriptor = VirtualFileSystem::the().open(move(path), error, O_NOFOLLOW_NOERROR, cwdInode());
  1048. if (!descriptor)
  1049. return error;
  1050. descriptor->stat(statbuf);
  1051. return 0;
  1052. }
  1053. int Process::sys$stat(const char* path, Unix::stat* statbuf)
  1054. {
  1055. VALIDATE_USER_WRITE(statbuf, sizeof(Unix::stat));
  1056. int error;
  1057. auto descriptor = VirtualFileSystem::the().open(move(path), error, 0, cwdInode());
  1058. if (!descriptor)
  1059. return error;
  1060. descriptor->stat(statbuf);
  1061. return 0;
  1062. }
  1063. int Process::sys$readlink(const char* path, char* buffer, size_t size)
  1064. {
  1065. VALIDATE_USER_READ(path, strlen(path));
  1066. VALIDATE_USER_WRITE(buffer, size);
  1067. int error;
  1068. auto descriptor = VirtualFileSystem::the().open(path, error, O_RDONLY | O_NOFOLLOW_NOERROR, cwdInode());
  1069. if (!descriptor)
  1070. return error;
  1071. if (!descriptor->metadata().isSymbolicLink())
  1072. return -EINVAL;
  1073. auto contents = descriptor->readEntireFile();
  1074. if (!contents)
  1075. return -EIO; // FIXME: Get a more detailed error from VFS.
  1076. memcpy(buffer, contents.pointer(), min(size, contents.size()));
  1077. if (contents.size() + 1 < size)
  1078. buffer[contents.size()] = '\0';
  1079. return 0;
  1080. }
  1081. int Process::sys$chdir(const char* path)
  1082. {
  1083. VALIDATE_USER_READ(path, strlen(path));
  1084. int error;
  1085. auto descriptor = VirtualFileSystem::the().open(path, error, 0, cwdInode());
  1086. if (!descriptor)
  1087. return error;
  1088. if (!descriptor->isDirectory())
  1089. return -ENOTDIR;
  1090. m_cwd = descriptor->vnode();
  1091. return 0;
  1092. }
  1093. int Process::sys$getcwd(char* buffer, size_t size)
  1094. {
  1095. VALIDATE_USER_WRITE(buffer, size);
  1096. auto path = VirtualFileSystem::the().absolutePath(cwdInode());
  1097. if (path.isNull())
  1098. return -EINVAL;
  1099. if (size < path.length() + 1)
  1100. return -ERANGE;
  1101. strcpy(buffer, path.characters());
  1102. return -ENOTIMPL;
  1103. }
  1104. size_t Process::number_of_open_file_descriptors() const
  1105. {
  1106. size_t count = 0;
  1107. for (auto& descriptor : m_file_descriptors) {
  1108. if (descriptor)
  1109. ++count;
  1110. }
  1111. return count;
  1112. }
  1113. int Process::sys$open(const char* path, int options)
  1114. {
  1115. #ifdef DEBUG_IO
  1116. kprintf("Process::sys$open(): PID=%u, path=%s {%u}\n", m_pid, path, pathLength);
  1117. #endif
  1118. VALIDATE_USER_READ(path, strlen(path));
  1119. if (number_of_open_file_descriptors() >= m_max_open_file_descriptors)
  1120. return -EMFILE;
  1121. int error;
  1122. auto descriptor = VirtualFileSystem::the().open(path, error, options, cwdInode());
  1123. if (!descriptor)
  1124. return error;
  1125. if (options & O_DIRECTORY && !descriptor->isDirectory())
  1126. return -ENOTDIR; // FIXME: This should be handled by VFS::open.
  1127. int fd = 0;
  1128. for (; fd < m_max_open_file_descriptors; ++fd) {
  1129. if (!m_file_descriptors[fd])
  1130. break;
  1131. }
  1132. m_file_descriptors[fd] = move(descriptor);
  1133. return fd;
  1134. }
  1135. int Process::sys$uname(utsname* buf)
  1136. {
  1137. VALIDATE_USER_WRITE(buf, sizeof(utsname));
  1138. strcpy(buf->sysname, "Serenity");
  1139. strcpy(buf->release, "1.0-dev");
  1140. strcpy(buf->version, "FIXME");
  1141. strcpy(buf->machine, "i386");
  1142. strcpy(buf->nodename, getHostname().characters());
  1143. return 0;
  1144. }
  1145. int Process::sys$isatty(int fd)
  1146. {
  1147. auto* descriptor = file_descriptor(fd);
  1148. if (!descriptor)
  1149. return -EBADF;
  1150. if (!descriptor->isTTY())
  1151. return -ENOTTY;
  1152. return 1;
  1153. }
  1154. int Process::sys$kill(pid_t pid, int signal)
  1155. {
  1156. if (pid == 0) {
  1157. // FIXME: Send to same-group processes.
  1158. ASSERT(pid != 0);
  1159. }
  1160. if (pid == -1) {
  1161. // FIXME: Send to all processes.
  1162. ASSERT(pid != -1);
  1163. }
  1164. ASSERT(pid != current->pid()); // FIXME: Support this scenario.
  1165. InterruptDisabler disabler;
  1166. auto* peer = Process::fromPID(pid);
  1167. if (!peer)
  1168. return -ESRCH;
  1169. peer->send_signal(signal, this);
  1170. return 0;
  1171. }
  1172. int Process::sys$sleep(unsigned seconds)
  1173. {
  1174. if (!seconds)
  1175. return 0;
  1176. sleep(seconds * TICKS_PER_SECOND);
  1177. return 0;
  1178. }
  1179. int Process::sys$gettimeofday(timeval* tv)
  1180. {
  1181. VALIDATE_USER_WRITE(tv, sizeof(tv));
  1182. InterruptDisabler disabler;
  1183. auto now = RTC::now();
  1184. tv->tv_sec = now;
  1185. tv->tv_usec = 0;
  1186. return 0;
  1187. }
  1188. uid_t Process::sys$getuid()
  1189. {
  1190. return m_uid;
  1191. }
  1192. gid_t Process::sys$getgid()
  1193. {
  1194. return m_gid;
  1195. }
  1196. uid_t Process::sys$geteuid()
  1197. {
  1198. return m_euid;
  1199. }
  1200. gid_t Process::sys$getegid()
  1201. {
  1202. return m_egid;
  1203. }
  1204. pid_t Process::sys$getpid()
  1205. {
  1206. return m_pid;
  1207. }
  1208. pid_t Process::sys$getppid()
  1209. {
  1210. return m_ppid;
  1211. }
  1212. mode_t Process::sys$umask(mode_t mask)
  1213. {
  1214. auto old_mask = m_umask;
  1215. m_umask = mask;
  1216. return old_mask;
  1217. }
  1218. pid_t Process::sys$waitpid(pid_t waitee, int* wstatus, int options)
  1219. {
  1220. if (wstatus)
  1221. VALIDATE_USER_WRITE(wstatus, sizeof(int));
  1222. InterruptDisabler disabler;
  1223. if (!Process::fromPID(waitee))
  1224. return -1;
  1225. m_waitee = waitee;
  1226. m_waitee_status = 0;
  1227. block(BlockedWait);
  1228. sched_yield();
  1229. if (wstatus)
  1230. *wstatus = m_waitee_status;
  1231. return m_waitee;
  1232. }
  1233. void Process::unblock()
  1234. {
  1235. ASSERT(m_state != Process::Runnable && m_state != Process::Running);
  1236. system.nblocked--;
  1237. m_state = Process::Runnable;
  1238. }
  1239. void Process::block(Process::State state)
  1240. {
  1241. ASSERT(current->state() == Process::Running);
  1242. system.nblocked++;
  1243. current->set_state(state);
  1244. }
  1245. void block(Process::State state)
  1246. {
  1247. current->block(state);
  1248. sched_yield();
  1249. }
  1250. void sleep(DWORD ticks)
  1251. {
  1252. ASSERT(current->state() == Process::Running);
  1253. current->setWakeupTime(system.uptime + ticks);
  1254. current->block(Process::BlockedSleep);
  1255. sched_yield();
  1256. }
  1257. Process* Process::kernelProcess()
  1258. {
  1259. ASSERT(s_kernelProcess);
  1260. return s_kernelProcess;
  1261. }
  1262. bool Process::isValidAddressForKernel(LinearAddress laddr) const
  1263. {
  1264. // We check extra carefully here since the first 4MB of the address space is identity-mapped.
  1265. // This code allows access outside of the known used address ranges to get caught.
  1266. InterruptDisabler disabler;
  1267. if (laddr.get() >= ksyms().first().address && laddr.get() <= ksyms().last().address)
  1268. return true;
  1269. if (is_kmalloc_address((void*)laddr.get()))
  1270. return true;
  1271. return validate_user_read(laddr);
  1272. }
  1273. bool Process::validate_user_read(LinearAddress laddr) const
  1274. {
  1275. InterruptDisabler disabler;
  1276. return MM.validate_user_read(*this, laddr);
  1277. }
  1278. bool Process::validate_user_write(LinearAddress laddr) const
  1279. {
  1280. InterruptDisabler disabler;
  1281. return MM.validate_user_write(*this, laddr);
  1282. }
  1283. pid_t Process::sys$getsid(pid_t pid)
  1284. {
  1285. if (pid == 0)
  1286. return m_sid;
  1287. InterruptDisabler disabler;
  1288. auto* process = Process::fromPID(pid);
  1289. if (!process)
  1290. return -ESRCH;
  1291. if (m_sid != process->m_sid)
  1292. return -EPERM;
  1293. return process->m_sid;
  1294. }
  1295. pid_t Process::sys$setsid()
  1296. {
  1297. InterruptDisabler disabler;
  1298. bool found_process_with_same_pgid_as_my_pid = false;
  1299. forEachProcess([&] (auto& process) {
  1300. if (process.pgid() == pid()) {
  1301. found_process_with_same_pgid_as_my_pid = true;
  1302. return false;
  1303. }
  1304. return true;
  1305. });
  1306. if (found_process_with_same_pgid_as_my_pid)
  1307. return -EPERM;
  1308. m_sid = m_pid;
  1309. m_pgid = m_pid;
  1310. return m_sid;
  1311. }
  1312. pid_t Process::sys$getpgid(pid_t pid)
  1313. {
  1314. if (pid == 0)
  1315. return m_pgid;
  1316. InterruptDisabler disabler; // FIXME: Use a ProcessHandle
  1317. auto* process = Process::fromPID(pid);
  1318. if (!process)
  1319. return -ESRCH;
  1320. return process->m_pgid;
  1321. }
  1322. pid_t Process::sys$getpgrp()
  1323. {
  1324. return m_pgid;
  1325. }
  1326. static pid_t get_sid_from_pgid(pid_t pgid)
  1327. {
  1328. InterruptDisabler disabler;
  1329. auto* group_leader = Process::fromPID(pgid);
  1330. if (!group_leader)
  1331. return -1;
  1332. return group_leader->sid();
  1333. }
  1334. int Process::sys$setpgid(pid_t specified_pid, pid_t specified_pgid)
  1335. {
  1336. InterruptDisabler disabler; // FIXME: Use a ProcessHandle
  1337. pid_t pid = specified_pid ? specified_pid : m_pid;
  1338. if (specified_pgid < 0)
  1339. return -EINVAL;
  1340. auto* process = Process::fromPID(pid);
  1341. if (!process)
  1342. return -ESRCH;
  1343. pid_t new_pgid = specified_pgid ? specified_pgid : process->m_pid;
  1344. pid_t current_sid = get_sid_from_pgid(process->m_pgid);
  1345. pid_t new_sid = get_sid_from_pgid(new_pgid);
  1346. if (current_sid != new_sid) {
  1347. // Can't move a process between sessions.
  1348. return -EPERM;
  1349. }
  1350. // FIXME: There are more EPERM conditions to check for here..
  1351. process->m_pgid = new_pgid;
  1352. return 0;
  1353. }
  1354. pid_t Process::sys$tcgetpgrp(int fd)
  1355. {
  1356. auto* descriptor = file_descriptor(fd);
  1357. if (!descriptor)
  1358. return -EBADF;
  1359. if (!descriptor->isTTY())
  1360. return -ENOTTY;
  1361. auto& tty = *descriptor->tty();
  1362. if (&tty != m_tty)
  1363. return -ENOTTY;
  1364. return tty.pgid();
  1365. }
  1366. int Process::sys$tcsetpgrp(int fd, pid_t pgid)
  1367. {
  1368. if (pgid < 0)
  1369. return -EINVAL;
  1370. if (get_sid_from_pgid(pgid) != m_sid)
  1371. return -EINVAL;
  1372. auto* descriptor = file_descriptor(fd);
  1373. if (!descriptor)
  1374. return -EBADF;
  1375. if (!descriptor->isTTY())
  1376. return -ENOTTY;
  1377. auto& tty = *descriptor->tty();
  1378. if (&tty != m_tty)
  1379. return -ENOTTY;
  1380. tty.set_pgid(pgid);
  1381. return 0;
  1382. }
  1383. int Process::sys$getdtablesize()
  1384. {
  1385. return m_max_open_file_descriptors;
  1386. }
  1387. int Process::sys$dup(int old_fd)
  1388. {
  1389. auto* descriptor = file_descriptor(old_fd);
  1390. if (!descriptor)
  1391. return -EBADF;
  1392. if (number_of_open_file_descriptors() == m_max_open_file_descriptors)
  1393. return -EMFILE;
  1394. int new_fd = 0;
  1395. for (; new_fd < m_max_open_file_descriptors; ++new_fd) {
  1396. if (!m_file_descriptors[new_fd])
  1397. break;
  1398. }
  1399. m_file_descriptors[new_fd] = descriptor;
  1400. return new_fd;
  1401. }
  1402. int Process::sys$dup2(int old_fd, int new_fd)
  1403. {
  1404. auto* descriptor = file_descriptor(old_fd);
  1405. if (!descriptor)
  1406. return -EBADF;
  1407. if (number_of_open_file_descriptors() == m_max_open_file_descriptors)
  1408. return -EMFILE;
  1409. m_file_descriptors[new_fd] = descriptor;
  1410. return new_fd;
  1411. }
  1412. Unix::sighandler_t Process::sys$signal(int signum, Unix::sighandler_t handler)
  1413. {
  1414. // FIXME: Fail with -EINVAL if attepmting to catch or ignore SIGKILL or SIGSTOP.
  1415. if (signum >= 32)
  1416. return (Unix::sighandler_t)-EINVAL;
  1417. dbgprintf("sys$signal: %d => L%x\n", signum, handler);
  1418. return nullptr;
  1419. }
  1420. int Process::sys$sigaction(int signum, const Unix::sigaction* act, Unix::sigaction* old_act)
  1421. {
  1422. // FIXME: Fail with -EINVAL if attepmting to change action for SIGKILL or SIGSTOP.
  1423. if (signum >= 32)
  1424. return -EINVAL;
  1425. VALIDATE_USER_READ(act, sizeof(Unix::sigaction));
  1426. InterruptDisabler disabler; // FIXME: This should use a narrower lock.
  1427. auto& action = m_signal_action_data[signum];
  1428. if (old_act) {
  1429. VALIDATE_USER_WRITE(old_act, sizeof(Unix::sigaction));
  1430. old_act->sa_flags = action.flags;
  1431. old_act->sa_restorer = (decltype(old_act->sa_restorer))action.restorer.get();
  1432. old_act->sa_sigaction = (decltype(old_act->sa_sigaction))action.handler_or_sigaction.get();
  1433. }
  1434. action.restorer = LinearAddress((dword)act->sa_restorer);
  1435. action.flags = act->sa_flags;
  1436. action.handler_or_sigaction = LinearAddress((dword)act->sa_sigaction);
  1437. return 0;
  1438. }
  1439. int Process::sys$getgroups(int count, gid_t* gids)
  1440. {
  1441. if (count < 0)
  1442. return -EINVAL;
  1443. ASSERT(m_gids.size() < MAX_PROCESS_GIDS);
  1444. if (!count)
  1445. return m_gids.size();
  1446. if (count != m_gids.size())
  1447. return -EINVAL;
  1448. VALIDATE_USER_WRITE(gids, sizeof(gid_t) * count);
  1449. size_t i = 0;
  1450. for (auto gid : m_gids)
  1451. gids[i++] = gid;
  1452. return 0;
  1453. }
  1454. int Process::sys$setgroups(size_t count, const gid_t* gids)
  1455. {
  1456. if (!is_root())
  1457. return -EPERM;
  1458. if (count >= MAX_PROCESS_GIDS)
  1459. return -EINVAL;
  1460. VALIDATE_USER_READ(gids, sizeof(gid_t) * count);
  1461. m_gids.clear();
  1462. m_gids.set(m_gid);
  1463. for (size_t i = 0; i < count; ++i)
  1464. m_gids.set(gids[i]);
  1465. return 0;
  1466. }