2021-03-24 09:12:03 +01:00
|
|
|
/****************************************************************************
|
2013-02-16 17:32:19 +01:00
|
|
|
* arch/arm/src/armv6-m/vfork.S
|
|
|
|
*
|
2021-03-24 09:11:24 +01:00
|
|
|
* Licensed to the Apache Software Foundation (ASF) under one or more
|
|
|
|
* contributor license agreements. See the NOTICE file distributed with
|
|
|
|
* this work for additional information regarding copyright ownership. The
|
|
|
|
* ASF licenses this file to you under the Apache License, Version 2.0 (the
|
|
|
|
* "License"); you may not use this file except in compliance with the
|
|
|
|
* License. You may obtain a copy of the License at
|
2013-02-16 17:32:19 +01:00
|
|
|
*
|
2021-03-24 09:11:24 +01:00
|
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
2013-02-16 17:32:19 +01:00
|
|
|
*
|
2021-03-24 09:11:24 +01:00
|
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
|
|
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
|
|
|
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
|
|
|
* License for the specific language governing permissions and limitations
|
|
|
|
* under the License.
|
2013-02-16 17:32:19 +01:00
|
|
|
*
|
2021-03-24 09:12:03 +01:00
|
|
|
****************************************************************************/
|
2013-02-16 17:32:19 +01:00
|
|
|
|
2021-03-24 09:12:03 +01:00
|
|
|
/****************************************************************************
|
2013-02-16 17:32:19 +01:00
|
|
|
* Included Files
|
2021-03-24 09:12:03 +01:00
|
|
|
****************************************************************************/
|
2013-02-16 17:32:19 +01:00
|
|
|
|
|
|
|
#include <nuttx/config.h>
|
|
|
|
|
2020-05-01 03:20:29 +02:00
|
|
|
#include "arm_vfork.h"
|
2013-02-16 17:32:19 +01:00
|
|
|
|
2021-03-24 09:12:03 +01:00
|
|
|
/****************************************************************************
|
2013-02-16 17:32:19 +01:00
|
|
|
* Pre-processor Definitions
|
2021-03-24 09:12:03 +01:00
|
|
|
****************************************************************************/
|
2013-02-16 17:32:19 +01:00
|
|
|
|
2021-03-24 09:12:03 +01:00
|
|
|
/****************************************************************************
|
2015-10-03 01:42:29 +02:00
|
|
|
* Public Symbols
|
2021-03-24 09:12:03 +01:00
|
|
|
****************************************************************************/
|
2013-02-16 17:32:19 +01:00
|
|
|
|
|
|
|
.file "vfork.S"
|
|
|
|
.globl up_vfork
|
|
|
|
|
2021-03-24 09:12:03 +01:00
|
|
|
/****************************************************************************
|
2013-02-16 17:32:19 +01:00
|
|
|
* Public Functions
|
2021-03-24 09:12:03 +01:00
|
|
|
****************************************************************************/
|
2013-02-16 17:32:19 +01:00
|
|
|
|
2021-03-24 09:12:03 +01:00
|
|
|
/****************************************************************************
|
2013-02-16 17:32:19 +01:00
|
|
|
* Name: vfork
|
|
|
|
*
|
|
|
|
* Description:
|
2021-04-01 12:12:05 +02:00
|
|
|
* The vfork() function has the same effect as fork(), except that the
|
|
|
|
* behavior is undefined if the process created by vfork() either modifies
|
|
|
|
* any data other than a variable of type pid_t used to store the return
|
|
|
|
* value from vfork(), or returns from the function in which vfork() was
|
|
|
|
* called, or calls any other function before successfully calling _exit()
|
|
|
|
* or one of the exec family of functions.
|
2013-02-16 17:32:19 +01:00
|
|
|
*
|
2021-04-01 12:12:05 +02:00
|
|
|
* This thin layer implements vfork by simply calling up_vfork() with the
|
|
|
|
* vfork() context as an argument. The overall sequence is:
|
2013-02-16 17:32:19 +01:00
|
|
|
*
|
|
|
|
* 1) User code calls vfork(). vfork() collects context information and
|
|
|
|
* transfers control up up_vfork().
|
2021-04-12 17:44:08 +02:00
|
|
|
* 2) up_vfork() and calls nxtask_setup_vfork().
|
2021-04-01 12:12:05 +02:00
|
|
|
* 3) nxtask_setup_vfork() allocates and configures the child task's TCB.
|
|
|
|
* This consists of:
|
2013-02-16 17:32:19 +01:00
|
|
|
* - Allocation of the child task's TCB.
|
|
|
|
* - Initialization of file descriptors and streams
|
|
|
|
* - Configuration of environment variables
|
2021-04-12 17:44:08 +02:00
|
|
|
* - Allocate and initialize the stack
|
2020-02-23 09:50:23 +01:00
|
|
|
* - Setup the input parameters for the task.
|
2021-04-12 17:44:08 +02:00
|
|
|
* - Initialization of the TCB (including call to up_initial_state())
|
2013-02-16 17:32:19 +01:00
|
|
|
* 4) up_vfork() provides any additional operating context. up_vfork must:
|
|
|
|
* - Initialize special values in any CPU registers that were not
|
|
|
|
* already configured by up_initial_state()
|
2020-05-16 17:06:29 +02:00
|
|
|
* 5) up_vfork() then calls nxtask_start_vfork()
|
|
|
|
* 6) nxtask_start_vfork() then executes the child thread.
|
2013-02-16 17:32:19 +01:00
|
|
|
*
|
2018-02-01 17:00:02 +01:00
|
|
|
* Input Parameters:
|
2013-02-16 17:32:19 +01:00
|
|
|
* None
|
|
|
|
*
|
2018-02-01 17:00:02 +01:00
|
|
|
* Returned Value:
|
2021-04-01 12:12:05 +02:00
|
|
|
* Upon successful completion, vfork() returns 0 to the child process and
|
|
|
|
* returns the process ID of the child process to the parent process.
|
|
|
|
* Otherwise, -1 is returned to the parent, no child process is created,
|
|
|
|
* and errno is set to indicate the error.
|
2013-02-16 17:32:19 +01:00
|
|
|
*
|
2021-03-24 09:12:03 +01:00
|
|
|
****************************************************************************/
|
2013-02-16 17:32:19 +01:00
|
|
|
|
|
|
|
.align 2
|
|
|
|
.code 16
|
|
|
|
.thumb_func
|
|
|
|
.globl vfork
|
|
|
|
.type vfork, function
|
|
|
|
vfork:
|
|
|
|
/* Create a stack frame */
|
|
|
|
|
2021-04-01 12:12:05 +02:00
|
|
|
mov r0, sp /* Save the value of the stack on entry */
|
2013-02-16 17:32:19 +01:00
|
|
|
sub sp, sp, #VFORK_SIZEOF /* Allocate the structure on the stack */
|
|
|
|
|
|
|
|
/* CPU registers */
|
|
|
|
/* Save the volatile registers */
|
|
|
|
|
|
|
|
mov r1, sp
|
2021-04-01 12:12:05 +02:00
|
|
|
stmia r1!, {r4-r7} /* Save r4-r7 in the structure */
|
|
|
|
mov r4, r8 /* Copy high registers to low registers */
|
2013-02-16 17:32:19 +01:00
|
|
|
mov r5, r9
|
|
|
|
mov r6, r10
|
|
|
|
mov r7, fp
|
2021-04-01 12:12:05 +02:00
|
|
|
stmia r1!, {r4-r7} /* Save r8-r10 and fp in the structure */
|
|
|
|
mov r5, lr /* Copy lr to a low register */
|
|
|
|
stmia r1!, {r0,r5} /* Save sp and lr in the structure */
|
2013-02-16 17:32:19 +01:00
|
|
|
|
|
|
|
/* Then, call up_vfork(), passing it a pointer to the stack structure */
|
|
|
|
|
|
|
|
mov r0, sp
|
|
|
|
bl up_vfork
|
|
|
|
|
|
|
|
/* Recover r4-r7 that were destroyed before up_vfork was called */
|
|
|
|
|
|
|
|
mov r1, sp
|
2021-04-01 12:12:05 +02:00
|
|
|
ldmia r1!, {r4-r7}
|
2013-02-16 17:32:19 +01:00
|
|
|
|
|
|
|
/* Release the stack data and return the value returned by up_vfork */
|
|
|
|
|
|
|
|
ldr r1, [sp, #VFORK_LR_OFFSET]
|
|
|
|
mov r14, r1
|
|
|
|
add sp, sp, #VFORK_SIZEOF
|
|
|
|
bx lr
|
|
|
|
.size vfork, .-vfork
|
|
|
|
.end
|