]> git.saurik.com Git - apple/xnu.git/blobdiff - bsd/kern/kern_exec.c
xnu-344.21.74.tar.gz
[apple/xnu.git] / bsd / kern / kern_exec.c
index 88348db3ff6a14cfe7b34cbdd60984a0cc954502..88b0a60c3ada531a0a271af0b9887ab0aec429dc 100644 (file)
@@ -1,21 +1,24 @@
 /*
- * Copyright (c) 2000 Apple Computer, Inc. All rights reserved.
+ * Copyright (c) 2000-2001 Apple Computer, Inc. All rights reserved.
  *
  * @APPLE_LICENSE_HEADER_START@
  * 
- * The contents of this file constitute Original Code as defined in and
- * are subject to the Apple Public Source License Version 1.1 (the
- * "License").  You may not use this file except in compliance with the
- * License.  Please obtain a copy of the License at
- * http://www.apple.com/publicsource and read it before using this file.
+ * Copyright (c) 1999-2003 Apple Computer, Inc.  All Rights Reserved.
  * 
- * This Original Code and all software distributed under the License are
- * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
+ * This file contains Original Code and/or Modifications of Original Code
+ * as defined in and that are subject to the Apple Public Source License
+ * Version 2.0 (the 'License'). You may not use this file except in
+ * compliance with the License. Please obtain a copy of the License at
+ * http://www.opensource.apple.com/apsl/ and read it before using this
+ * file.
+ * 
+ * The Original Code and all software distributed under the License are
+ * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
  * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
  * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT.  Please see the
- * License for the specific language governing rights and limitations
- * under the License.
+ * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
+ * Please see the License for the specific language governing rights and
+ * limitations under the License.
  * 
  * @APPLE_LICENSE_HEADER_END@
  */
@@ -94,6 +97,7 @@
 
 #include <vm/vm_map.h>
 #include <vm/vm_kern.h>
+#include <vm/vm_shared_memory_server.h>
 
 #include <kern/thread.h>
 #include <kern/task.h>
 #include <mach-o/fat.h>
 #include <mach-o/loader.h>
 #include <machine/vmparam.h>
+#if KTRACE   
+#include <sys/ktrace.h>
+#endif
+
+int    app_profile = 0;
 
 extern vm_map_t bsd_pageable_map;
 
@@ -160,6 +169,7 @@ execve(p, uap, retval)
        vm_map_t old_map;
        vm_map_t map;
        int i;
+       boolean_t               clean_regions = FALSE;
        union {
                /* #! and name of interpreter */
                char                    ex_shell[SHSIZE];
@@ -181,6 +191,7 @@ execve(p, uap, retval)
        int vfexec=0;
        unsigned long arch_offset =0;
        unsigned long arch_size = 0;
+        char           *ws_cache_name = NULL;  /* used for pre-heat */
 
        task = current_task();
        thr_act = current_act();
@@ -214,7 +225,7 @@ execve(p, uap, retval)
         * We have to do this before namei() because in case of
         * symbolic links, namei() would overwrite the original "path".
         * In case the last symbolic link resolved was a relative pathname
-        * we would loose the original "path", which could be an
+        * we would lose the original "path", which could be an
         * absolute pathname. This might be unacceptable for dyld.
         */
        /* XXX We could optimize to avoid copyinstr in the namei() */
@@ -226,6 +237,22 @@ execve(p, uap, retval)
         * copyinstr will put in savedpathlen, the count of
         * characters (including NULL) in the path.
         */
+
+       if(app_profile != 0) {
+
+               /* grab the name of the file out of its path */
+               /* we will need this for lookup within the   */
+               /* name file */
+               ws_cache_name = savedpath + savedpathlen;
+                       while (ws_cache_name[0] != '/') {
+                               if(ws_cache_name == savedpath) {
+                                       ws_cache_name--;
+                                       break;
+                       }
+                               ws_cache_name--;
+                       }
+                       ws_cache_name++;
+       }
        
        /* Save the name aside for future use */
        execargsp = (vm_offset_t *)((char *)(execargs) + savedpathlen);
@@ -489,6 +516,8 @@ again:
                printf("execve: task_create failed. Code: 0x%x\n", result);
                p->task = new_task;
                set_bsdtask_info(new_task, p);
+               if (p->p_nice != 0)
+                       resetpriority(p);
                task = new_task;
                map = get_task_map(new_task);
                result = thread_create(new_task, &thr_act);
@@ -504,8 +533,13 @@ again:
         *      Load the Mach-O file.
         */
        VOP_UNLOCK(vp, 0, p);
+       if(ws_cache_name) {
+               tws_handle_startup_file(task, cred->cr_uid, 
+                       ws_cache_name, vp, &clean_regions);
+       }
+
        lret = load_machfile(vp, mach_header, arch_offset,
-                               arch_size, &load_result, thr_act, map);
+               arch_size, &load_result, thr_act, map, clean_regions);
 
        if (lret != LOAD_SUCCESS) {
                error = load_return_to_errno(lret);
@@ -580,10 +614,8 @@ again:
        p->p_cred->p_svuid = p->p_ucred->cr_uid;
        p->p_cred->p_svgid = p->p_ucred->cr_gid;
 
-       if (!vfexec && (p->p_flag & P_TRACED)) {
+       if (!vfexec && (p->p_flag & P_TRACED))
                psignal(p, SIGTRAP);
-               ast_on(AST_BSD);
-       }
 
        if (error) {
                goto badtoolate;
@@ -647,7 +679,11 @@ again:
                 * and NBPW for the NULL after pointer to path.
                 */
                ap = ucp - na*NBPW - 3*NBPW - savedpathlen - 2*NBPW;
+#if defined(ppc)
+               thread_setuserstack(thr_act, ap);       /* Set the stack */
+#else
                uthread->uu_ar0[SP] = ap;
+#endif
                (void) suword((caddr_t)ap, na-ne); /* argc */
                nc = 0;
                cc = 0;
@@ -682,14 +718,20 @@ again:
        }
        
        if (load_result.dynlinker) {
+#if defined(ppc)
+               ap = thread_adjuserstack(thr_act, -4);  /* Adjust the stack */
+#else
                ap = uthread->uu_ar0[SP] -= 4;
+#endif
                (void) suword((caddr_t)ap, load_result.mach_header);
        }
 
        if (vfexec) {
                vm_map_switch(old_map);
        }
-#if defined(i386) || defined(ppc)
+#if defined(ppc)
+       thread_setentrypoint(thr_act, load_result.entry_point); /* Set the entry point */
+#elif defined(i386) 
        uthread->uu_ar0[PC] = load_result.entry_point;
 #else
 #error architecture not implemented!
@@ -701,7 +743,7 @@ again:
        /*
         * Reset signal state.
         */
-       execsigs(p);
+       execsigs(p, thr_act);
 
        /*
         * Close file descriptors
@@ -709,8 +751,10 @@ again:
         */
        fdexec(p);
        /* FIXME: Till vmspace inherit is fixed: */
-       if (p->vm_shm)
+       if (!vfexec && p->vm_shm)
                shmexit(p);
+       /* Clean up the semaphores */
+       semexit(p);
 
        /*
         * Remember file name for accounting.
@@ -753,7 +797,6 @@ again:
 
 badtoolate:
        if (vfexec) {
-               (void) thread_resume(thr_act);
                task_deallocate(new_task);
                act_deallocate(thr_act);
                if (error)
@@ -768,6 +811,7 @@ bad1:
                execargs_free(execargs);
        if (!error && vfexec) {
                        vfork_return(current_act(), p->p_pptr, p, retval);
+                       (void) thread_resume(thr_act);
                        return(0);
        }
        return(error);
@@ -788,8 +832,8 @@ create_unix_stack(map, user_stack, customstack, p)
 
        p->user_stack = user_stack;
        if (!customstack) {
-               size = round_page(unix_stack_size(p));
-               addr = trunc_page(user_stack - size);
+               size = round_page_64(unix_stack_size(p));
+               addr = trunc_page_32(user_stack - size);
                return (vm_allocate(map,&addr, size, FALSE));
        } else
                return(KERN_SUCCESS);
@@ -816,8 +860,6 @@ load_init_program(p)
        register_t retval[2];
        struct uthread * ut;
 
-       unix_master();
-
        error = 0;
 
        /* init_args are copied in string form directly from bootstrap */
@@ -910,8 +952,6 @@ load_init_program(p)
 
                error = execve(p,&init_exec_args,retval);
        } while (error);
-
-       unix_release();
 }
 
 /*