void appCopyPaste::CopyPage(MenuPageC* pageData) { if ((pageData == 0) || (!pageData->IsCopyable())) return; MenuPageArray pages(1); pages.AddTo(pageData); CopyPages(pages); }
//========================================================================= // Fork the current process. // Return the pid of the new process //========================================================================= unsigned short DoFork() { unsigned short pid; struct FCB *fcbin, *fcbout, *fcberr; // Copy task structure, with adjustments struct Task *task = (struct Task *) AllocKMem(sizeof(struct Task)); memcpy((char *) task, (char *) currentTask, sizeof(struct Task)); pid = task->pid = nextpid++; task->currentDirName = AllocKMem( (size_t) strlen(currentTask->currentDirName) + 1); strcpy(task->currentDirName, currentTask->currentDirName); task->parentPort = 0; // Create Page Directory task->cr3 = (long) VCreatePageDir(pid, currentTask->pid); Elf64_Ehdr *header = (Elf64_Ehdr *)UserCode; if ((header->e_ident)[1] != 'E')// Not the best of tests, but good enough CopyPages(UserCode, task); else { Elf64_Phdr *pheadertable = (Elf64_Phdr *)(UserCode + header->e_phoff); int i; for (i = 0; i < header->e_phnum; i++) { if (pheadertable[i].p_type == PT_LOAD) { CopyPages(pheadertable[i].p_vaddr, task); } } } // Copy user stack and kernel stack CopyPages(UserStack, task); //Page Tables to allow access to E1000 /*CreatePTEWithPT((struct PML4 *) task->cr3, registers, (long) registers, 0, 7); CreatePTEWithPT((struct PML4 *) task->cr3, registers + 0x1000, (long) registers + 0x1000, 0, 7); CreatePTEWithPT((struct PML4 *) task->cr3, registers + 0x2000, (long) registers + 0x2000, 0, 7); CreatePTEWithPT((struct PML4 *) task->cr3, registers + 0x3000, (long) registers + 0x3000, 0, 7); CreatePTEWithPT((struct PML4 *) task->cr3, registers + 0x4000, (long) registers + 0x4000, 0, 7); CreatePTEWithPT((struct PML4 *) task->cr3, registers + 0x5000, (long) registers + 0x5000, 0, 7);*/ task->forking = 1; // Create FCBs for STDI, STDOUT, and STDERR // STDIN fcbin = (struct FCB *) AllocKMem(sizeof(struct FCB)); fcbin->fileDescriptor = STDIN; fcbin->deviceType = KBD; task->fcbList = fcbin; // STDOUT fcbout = (struct FCB *) AllocKMem(sizeof(struct FCB)); fcbout->fileDescriptor = STDOUT; fcbout->deviceType = CONS; fcbin->nextFCB = fcbout; //STDERR fcberr = (struct FCB *) AllocKMem(sizeof(struct FCB)); fcberr->fileDescriptor = STDERR; fcberr->deviceType = CONS; fcbout->nextFCB = fcberr; fcberr->nextFCB = 0; task->FDbitmap = 7; // Run the forked process asm("pushf"); asm("cli"); LinkTask(task); asm("popf"); // We want the forked process to return to this point. So we // need to save the registers from here to the new task structure. SaveRegisters(task); // Return 0 to the forked process, the new pid to the forking one. if (pid == currentTask->pid) pid = 0; return pid; }