syscall_emul.cc (11907:48a3d32da9d8) | syscall_emul.cc (11908:2fd0307d03e9) |
---|---|
1/* 2 * Copyright (c) 2003-2005 The Regents of The University of Michigan 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are 7 * met: redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer; --- 612 unchanged lines hidden (view full) --- 621 uid_t hostOwner = owner; 622 uint32_t group = p->getSyscallArg(tc, index); 623 gid_t hostGroup = group; 624 625 int result = fchown(sim_fd, hostOwner, hostGroup); 626 return (result == -1) ? -errno : result; 627} 628 | 1/* 2 * Copyright (c) 2003-2005 The Regents of The University of Michigan 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are 7 * met: redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer; --- 612 unchanged lines hidden (view full) --- 621 uid_t hostOwner = owner; 622 uint32_t group = p->getSyscallArg(tc, index); 623 gid_t hostGroup = group; 624 625 int result = fchown(sim_fd, hostOwner, hostGroup); 626 return (result == -1) ? -errno : result; 627} 628 |
629 | |
630/** | 629/** |
631 * TODO: there's a bit more involved here since file descriptors created with 632 * dup are supposed to share a file description. So, there is a problem with 633 * maintaining fields like file offset or flags since an update to such a 634 * field won't be reflected in the metadata for the fd entries that we 635 * maintain to hold metadata for checkpoint restoration. | 630 * FIXME: The file description is not shared among file descriptors created 631 * with dup. Really, it's difficult to maintain fields like file offset or 632 * flags since an update to such a field won't be reflected in the metadata 633 * for the fd entries that we maintain for checkpoint restoration. |
636 */ 637SyscallReturn 638dupFunc(SyscallDesc *desc, int num, Process *p, ThreadContext *tc) 639{ 640 int index = 0; 641 int tgt_fd = p->getSyscallArg(tc, index); 642 643 auto old_hbfdp = std::dynamic_pointer_cast<HBFDEntry>((*p->fds)[tgt_fd]); 644 if (!old_hbfdp) 645 return -EBADF; 646 int sim_fd = old_hbfdp->getSimFD(); 647 648 int result = dup(sim_fd); | 634 */ 635SyscallReturn 636dupFunc(SyscallDesc *desc, int num, Process *p, ThreadContext *tc) 637{ 638 int index = 0; 639 int tgt_fd = p->getSyscallArg(tc, index); 640 641 auto old_hbfdp = std::dynamic_pointer_cast<HBFDEntry>((*p->fds)[tgt_fd]); 642 if (!old_hbfdp) 643 return -EBADF; 644 int sim_fd = old_hbfdp->getSimFD(); 645 646 int result = dup(sim_fd); |
649 int local_errno = errno; | 647 if (result == -1) 648 return -errno; |
650 | 649 |
651 std::shared_ptr<FDEntry> new_fdep = old_hbfdp->clone(); 652 auto new_hbfdp = std::dynamic_pointer_cast<HBFDEntry>(new_fdep); | 650 auto new_hbfdp = std::dynamic_pointer_cast<HBFDEntry>(old_hbfdp->clone()); |
653 new_hbfdp->setSimFD(result); | 651 new_hbfdp->setSimFD(result); |
652 new_hbfdp->setCOE(false); 653 return p->fds->allocFD(new_hbfdp); 654} |
|
654 | 655 |
655 return (result == -1) ? -local_errno : p->fds->allocFD(new_fdep); | 656SyscallReturn 657dup2Func(SyscallDesc *desc, int num, Process *p, ThreadContext *tc) 658{ 659 int index = 0; 660 661 int old_tgt_fd = p->getSyscallArg(tc, index); 662 auto old_hbp = std::dynamic_pointer_cast<HBFDEntry>((*p->fds)[old_tgt_fd]); 663 if (!old_hbp) 664 return -EBADF; 665 int old_sim_fd = old_hbp->getSimFD(); 666 667 /** 668 * We need a valid host file descriptor number to be able to pass into 669 * the second parameter for dup2 (newfd), but we don't know what the 670 * viable numbers are; we execute the open call to retrieve one. 671 */ 672 int res_fd = dup2(old_sim_fd, open("/dev/null", O_RDONLY)); 673 if (res_fd == -1) 674 return -errno; 675 676 int new_tgt_fd = p->getSyscallArg(tc, index); 677 auto new_hbp = std::dynamic_pointer_cast<HBFDEntry>((*p->fds)[new_tgt_fd]); 678 if (new_hbp) 679 p->fds->closeFDEntry(new_tgt_fd); 680 new_hbp = std::dynamic_pointer_cast<HBFDEntry>(old_hbp->clone()); 681 new_hbp->setSimFD(res_fd); 682 new_hbp->setCOE(false); 683 684 return p->fds->allocFD(new_hbp); |
656} 657 658SyscallReturn 659fcntlFunc(SyscallDesc *desc, int num, Process *p, ThreadContext *tc) 660{ 661 int arg; 662 int index = 0; 663 int tgt_fd = p->getSyscallArg(tc, index); --- 62 unchanged lines hidden (view full) --- 726 // not sure if this is totally valid, but we'll pass it through 727 // to the underlying OS 728 warn("fcntl64(%d, %d) passed through to host\n", tgt_fd, cmd); 729 return fcntl(sim_fd, cmd); 730 } 731} 732 733SyscallReturn | 685} 686 687SyscallReturn 688fcntlFunc(SyscallDesc *desc, int num, Process *p, ThreadContext *tc) 689{ 690 int arg; 691 int index = 0; 692 int tgt_fd = p->getSyscallArg(tc, index); --- 62 unchanged lines hidden (view full) --- 755 // not sure if this is totally valid, but we'll pass it through 756 // to the underlying OS 757 warn("fcntl64(%d, %d) passed through to host\n", tgt_fd, cmd); 758 return fcntl(sim_fd, cmd); 759 } 760} 761 762SyscallReturn |
734pipePseudoFunc(SyscallDesc *desc, int callnum, Process *process, 735 ThreadContext *tc) | 763pipeImpl(SyscallDesc *desc, int callnum, Process *p, ThreadContext *tc, 764 bool pseudoPipe) |
736{ | 765{ |
766 Addr tgt_addr = 0; 767 if (!pseudoPipe) { 768 int index = 0; 769 tgt_addr = p->getSyscallArg(tc, index); 770 } 771 |
|
737 int sim_fds[2], tgt_fds[2]; 738 739 int pipe_retval = pipe(sim_fds); | 772 int sim_fds[2], tgt_fds[2]; 773 774 int pipe_retval = pipe(sim_fds); |
740 if (pipe_retval < 0) 741 return pipe_retval; | 775 if (pipe_retval == -1) 776 return -errno; |
742 743 auto rend = PipeFDEntry::EndType::read; 744 auto rpfd = std::make_shared<PipeFDEntry>(sim_fds[0], O_WRONLY, rend); | 777 778 auto rend = PipeFDEntry::EndType::read; 779 auto rpfd = std::make_shared<PipeFDEntry>(sim_fds[0], O_WRONLY, rend); |
780 tgt_fds[0] = p->fds->allocFD(rpfd); |
|
745 746 auto wend = PipeFDEntry::EndType::write; 747 auto wpfd = std::make_shared<PipeFDEntry>(sim_fds[1], O_RDONLY, wend); | 781 782 auto wend = PipeFDEntry::EndType::write; 783 auto wpfd = std::make_shared<PipeFDEntry>(sim_fds[1], O_RDONLY, wend); |
784 tgt_fds[1] = p->fds->allocFD(wpfd); |
|
748 | 785 |
749 tgt_fds[0] = process->fds->allocFD(rpfd); 750 tgt_fds[1] = process->fds->allocFD(wpfd); 751 | |
752 /** 753 * Now patch the read object to record the target file descriptor chosen 754 * as the write end of the pipe. 755 */ 756 rpfd->setPipeReadSource(tgt_fds[1]); 757 758 /** 759 * Alpha Linux convention for pipe() is that fd[0] is returned as 760 * the return value of the function, and fd[1] is returned in r20. 761 */ | 786 /** 787 * Now patch the read object to record the target file descriptor chosen 788 * as the write end of the pipe. 789 */ 790 rpfd->setPipeReadSource(tgt_fds[1]); 791 792 /** 793 * Alpha Linux convention for pipe() is that fd[0] is returned as 794 * the return value of the function, and fd[1] is returned in r20. 795 */ |
762 tc->setIntReg(SyscallPseudoReturnReg, tgt_fds[1]); 763 return sim_fds[0]; | 796 if (pseudoPipe) { 797 tc->setIntReg(SyscallPseudoReturnReg, tgt_fds[1]); 798 return tgt_fds[0]; 799 } 800 801 /** 802 * Copy the target file descriptors into buffer space and then copy 803 * the buffer space back into the target address space. 804 */ 805 BufferArg tgt_handle(tgt_addr, sizeof(int[2])); 806 int *buf_ptr = (int*)tgt_handle.bufferPtr(); 807 buf_ptr[0] = tgt_fds[0]; 808 buf_ptr[1] = tgt_fds[1]; 809 tgt_handle.copyOut(tc->getMemProxy()); 810 return 0; |
764} 765 766SyscallReturn | 811} 812 813SyscallReturn |
814pipePseudoFunc(SyscallDesc *desc, int callnum, Process *process, 815 ThreadContext *tc) 816{ 817 return pipeImpl(desc, callnum, process, tc, true); 818} 819 820SyscallReturn 821pipeFunc(SyscallDesc *desc, int callnum, Process *process, ThreadContext *tc) 822{ 823 return pipeImpl(desc, callnum, process, tc, false); 824} 825 826SyscallReturn |
|
767setpgidFunc(SyscallDesc *desc, int callnum, Process *process, 768 ThreadContext *tc) 769{ 770 int index = 0; 771 int pid = process->getSyscallArg(tc, index); 772 int pgid = process->getSyscallArg(tc, index); 773 774 if (pgid < 0) --- 169 unchanged lines hidden --- | 827setpgidFunc(SyscallDesc *desc, int callnum, Process *process, 828 ThreadContext *tc) 829{ 830 int index = 0; 831 int pid = process->getSyscallArg(tc, index); 832 int pgid = process->getSyscallArg(tc, index); 833 834 if (pgid < 0) --- 169 unchanged lines hidden --- |