For safety and efficiency, sendmail undertakes a complicated series of steps to run (execute) a delivery agent.  Some (such as setting the environment) are intended to improve security. Others (such as forking) are intended to improve efficiency by creating parallel actions. Here, we discuss those steps in the order in which they are taken by sendmail.
 For the purpose of this discussion we will exclude the internal agents (such as IPC) and focus on actual programs (such as /bin/mail).
If sendmail is running in verbose mode (see Section 34.8.76, Verbose), it shows that it is about to start this process:
Connecting to delivery agent
If a traffic-logging file was specified with
command-line switch (see Section 26.4, "Log Transactions with -X"), sendmail appends the
following line to that file:
pid === EXEC the expanded A= here
A= equate (see Section 30.4.1) from the delivery
agent's declaration is printed with all its macros expanded
and with the recipients listed.
Next sendmail creates a pipe so that it
will be able to print the email message to the
delivery agent and so that it can read errors
emitted by the delivery agent. See the
switch (see Section 37.5.44, -d11.1) for a description of what
can go wrong.
If all has gone well, sendmail fork(2)s a copy of itself. The parent then pipes the email message to the child.
If sendmail was compiled with HASSETUSERCONTEXT defined (see Section 18.8.9, HAS...), it calls setusercontext(3) like this:
pwd is a pointer to a structure of type
passwd for the user whose uid is
uid is that of the controlling user
(see Section 24.2.2, "Delivery to Files") or the
recipient (see Section 30.8.33, F=o).
N= equate (see Section 30.4.8) has a
nonzero value, sendmail calls nice(3) to "re-nice"
the delivery agent to that value.
The sendmail program next sets its uid and
gid as appropriate. If the
(see Section 34.8.19, DontInitGroups) is false, sendmail
The identity used is that described under the
option (see Section 34.8.15).
Finally, sendmail calls setsid(2) to become a process-group leader and execve(2) to become the delivery agent. That latter call looks like this:
agent is the full path of the delivery agent
as specified in the
P= equate (see Section 30.4.9).
The argument vector (contents of the
A= equate with
all the macros expanded and all the recipients added) is passed
argv. The environment is that originally given
to sendmail, massaged for security and augmented
E= configuration command (see Section 22.2.1).