ChinaFAQ论坛

 找回密码
 立即注册
搜索
热搜: 活动 交友 discuz
查看: 2122|回复: 0

在Mac OS X中,有三种方式来实现启动项

[复制链接]

75

主题

76

帖子

422

积分

管理员

CEO

Rank: 9Rank: 9Rank: 9

积分
422
QQ
发表于 2020-4-2 22:48:17 | 显示全部楼层 |阅读模式
在Mac OS X中,有三种方式来实现启动项的配置:1)Login Items;2)StartupItems;3)launchd daemon。+ z# K% I+ S* I3 _! ?$ T. ]' O
& P: U! Y8 e6 Z# ?# X
1.Login Items/ o8 ]- k4 I4 f" ]- B+ }7 \. W3 G
打开System Preferences,选择System -> Accounts,选择Login Items选项卡,将/Applications目录下的.app直接拖进右边的列表中。重启电脑之后就会发现列表中的程序在开机之后就自动启动了。5 Q7 S# [, A5 Q* ~# R

1 @' N2 r; l) B3 q
, i6 f, Q, d* R6 J& P1 [6 L: {, s. v0 k$ k0 q$ ?  \
2.StartupItems
% I5 l- J, f+ |0 A2 uStartupItems,顾名思义,就是在系统启动过程中运行的程序,它们可以是运行完就立即终止的程序(比如,开机清空废纸篓),也可以是一直持续在系统运行周期的后台进程。
* ]; b! ~3 J  b4 |. [5 Y  a/ N1 M( F7 L6 R* T) v
StartupItems一般存放在以下两个路径下:% K- F2 y' }: f+ B6 h0 O- ]
. L6 Y, c* j& m
1)/System/Library/StartupItems, l0 r% ]; ]) y1 E: L' p  e4 F
- Y$ {1 u$ Q7 s8 V6 g7 A) a
2)/Library/StartupItems
; o: m5 k7 _! s) x  O9 |/ P! @" r( y% _2 x3 ]8 H
大部分与系统相关的StartupItems都放在/System/Library/StartupItems这个路径下,它们会先于/Library/StartupItems路径下的执行,因为前者路径下的StartupItems提供了系统级的基础服务,比如crash reporting,core graphics services,system accounting等,而后者路径在默认情况下是不存在的,需要自己手动创建。0 s( _, J' K7 X6 C" ~

* `0 P" `0 W% p- O' C% m( w这里我们以/Library/StartupItems目录下的IcebergControlTower为例。
, C. \# S& C9 D& m8 M+ e4 g3 @* ]1 k2 W6 Q9 _, d

# [! T6 W: G0 U' M1 F8 Z  n) M& o/ B( `6 ^( I- k
简单来说,在Mac OS X上,一个StartupItems包含以下两个方面的内容:
% {  n9 _1 w  N8 R3 x# N" s% o  J* y; M" ^9 H5 k2 _
1)可执行程序;
" G1 z( Z" W5 Q! _
+ g$ h) O9 f- @$ \2)包含依赖进程关系的plist文件(StartupParameters.plist)。! }. ~4 b! @. _! Z) J2 |( s/ ?8 I

5 h9 y' h  U3 u  ^/ M$ h" C2.1 The Property List
& h* f: w: W' N* J7 F. w6 H% p2.1.1 Plist的key值与含义
6 J, n8 J7 v" v: u1 [StartupParameters.plist 是一个属性列表,包含了运行可执行程序的必要条件。% F/ P2 F! w# q( a  V
" H7 U3 y7 l0 Z9 f' ]& t6 n# y
' t- J6 I  N- M, L" ]

# z- j0 I) J* }' p该plist需要获得root权限,包含了几个方面的内容:1 v# W' H5 L4 P4 b% g# F3 U$ L
6 l# o3 h7 R+ }" U
1)Description;
1 {( ~+ ^+ O! ~; [5 B+ l& R' h! @4 a# Q& G
      对该服务的一个简单的描述,仅仅是描述,并不是说明实际的进程名称。% a# L4 J5 x* E

9 d: I7 ^2 p0 J2)Provides;
9 E+ j' X! j& t% \" f0 D0 |6 D8 Z( e
      指定StartupItems提供的服务。如图plist文件Provides中说明,StartupItems开启的后台进程名为:Iceberg Control Tower。
/ Q% c9 K9 L& y$ f. W
& q) u  K  }8 I- d1 y5 l      Provides可以指定多个服务,反映在图中就是Item0,Item1…等。这里只有Item0。
0 ?; D0 A0 b" \3 F$ A+ c
  ?& d( _. U6 m0 A& @+ J$ |3)Uses;; |- Z- s. |% t# V/ _  o, P

6 V' U% U! j/ y* V9 t     指定了在StartupItems加载之前需要开启的服务。Mac OS X系统先尝试着加载Uses中指定的服务,然后再加载StartupItems。也就是说,即使Uses中指定的服务没有加载成功,系统仍然会加载StartupItems。
: z/ K0 ~" L$ A! l9 _6 V/ D3 \) O& h$ d. n( m
4)OrderPreference;
( D- r- l$ O* F% O" Y' u$ k# F+ x$ W4 k& A3 ?4 H" z
     指定执行StartupItems的时间顺序。这个顺序的重要程度排在Uses之后,是指定执行完Uses之后的顺序。可能的取值包括:First, Early, None(default), Late, Last。" }& _+ [' i6 q' Z( ~8 q3 E

; x% l/ N% G* K: M6 F5 W5)Messages。
) v# Y) u) [! c. s# Y& r: o
1 [. B, Z3 P7 ^) Y2.1.2 创建一个StartupParameters.plist文件
/ d5 B/ F3 |* Z! ^+ ~" n! ]<?xml version="1.0" encoding="UTF-8"?>
# O* U% f  p  W+ k2 B# V$ B( U9 m( s<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN"
! c! ]  i; s% e2 O: ?    "http://www.apple.com/DTDs/PropertyList-1.0.dtd">0 l& c" @. f& ?% }
<plist version="1.0">- n5 M" D- `0 M* w0 r$ f
<dict>
" V, T9 C0 a* R' y8 K& q6 o    <key>Description</key>
9 a* B2 u' X% O* m3 U        <string>Iceberg Control Tower Initilaization</string>' {) [" V$ O4 f% V5 r. d$ ?
    <key>Provides</key>4 Y9 q" T6 t6 H. M8 r6 f0 ^0 h
        <array>
. b" P- U  E9 z8 ^4 @8 Z, o+ ?3 |            <string>Iceberg Control Tower</string>
3 R# O6 M8 B5 c        </array>$ ^; T6 e- t+ |2 _9 l
     <key>Uses</key>3 l- M3 v+ \! F0 W9 P! P% v
        <array>
# C, j2 C1 Y$ ]  P# e            <string>Disks</string>8 G5 a- B2 D9 K# s; g7 \
        </array>, o, C# P2 H8 e
    <key>OrderPreference</key>' q! o( o( R/ _( C
        <string>None</string>- ~% d) V/ o- m
</dict>) a! O& d  S/ `) w
</plist>( J3 H, o4 ^+ K  E9 R0 l

1 {; W' w2 Y/ [, Z7 Q
! o9 g. n8 L, ~1 c
" {3 Z. w6 O& G( F. _$ q* g1 j8 U2.2 The Executable File5 N8 Q* E, [2 {& |: u5 B
注意:1)可执行文件的名称和它所在的文件夹的文件名是一样的,这是系统默认的规则。! J4 a5 ?6 A; }  U; r8 q& a5 [1 e

% s  ^# M( T$ ^" u6 G      2)操作可执行文件需要获得root权限。0 N- I3 p6 n. h
+ K) Y; E/ }; S
      3)可执行文件是一个shell脚本。3 K0 n9 C( n- }8 w" i- Y  _

' h7 b( D7 @$ l' Z$ @% f打开IcebergControlTower文件目录下同名的可执行文件,可以看到脚本的具体内容:
, S8 q# C3 l1 ?4 Z7 u+ A. c: m. y; H) M: I$ k% |. y2 O

* Z% z. Q* t; E$ v5 s2 v3 `* l/ O" X. k8 N, F; ?# v6 k+ J
一般的可执行文件包含这样几个方面的内容:! B! s& z1 E* j9 S& `9 I0 T& F, d

3 p$ a4 v& S* K) {) f! u1 u4 d1)./etc/rc.common' [$ x# P  m# e' c; V. Z

$ `$ x# W9 b# M" RApple提供的一个脚本库,该脚本库里包含了为可执行文件引进参数的接口。在这里load这个库主要是调用RunService。0 J- _4 O6 w. ^/ a  D, l) U. J
' j( Q! r3 I1 w
2)StartService(), StopService(), RestartService()5 o+ W9 t% w7 X6 P5 G0 w; s
4 {( R9 N* w$ [! ?& k9 C
当可执行文件接收到的参数为start,stop或者restart时,执行相对应的函数。
/ _' ^4 Z# p3 J6 L& v
! C; x$ [% E& U参数含义:
$ K) @1 L; W; m3 a- j# ~  Q
- g) t3 [, B  z8 ~start:开机过程中开启服务;
: {1 J# ~3 |/ `) x  J. t
, G! C. ?  l1 C2 W, g) Bstop:关机过程中停止服务;
. U. e5 ?" [9 v3 F6 L# ~+ K& O0 k+ s7 K3 k  D) P
restart:在特定条件下重启服务。
2 v8 D) y( c, t- v! @7 }/ v9 T  C! }& o, o, @
3)RunService  “$1”
2 e% Z2 U" l' Z. m" ^/ T
# @' G* P3 u: I2 u0 S/ R- x. Z执行传递给该脚本的第一个参数指定的服务。% _: X. @: @0 ]! E4 d: r5 s( r
# a* E# Q% c* w
“$1” 表示传给该脚本的第一个参数。例如,传入的参数为start,则执行StartService()。+ n3 s7 f3 A9 G/ R( w  F" |+ P
2 h0 }9 ?) s2 W! B7 E2 z
3. Launchd Daemon( G( e1 C+ ~5 r, Y( s7 F# u7 N
launchd是Mac OS下用于初始化系统环境的关键进程,它是内核装载成功之后在OS环境下启动的第一个进程。
6 M1 W: x2 a  x* _/ o
6 |# C" m% h* {0 j采用这种方式来配置自启动项很简单,只需要一个plist文件,通常(同时也是系统推荐)是将plist放在~/Library/LaunchAgents路径下。( |6 c: T2 q: i/ w" o& D4 K- T
, q6 T+ k: }6 Z$ S& Z2 T4 s$ u6 `
3.1 plist文件格式及每个字段的含义:/ s& V: \8 x/ f9 M1 Y  h" c
/ a$ U$ s/ ]) S- G9 a
" U( S* C9 `/ f! O5 `# B* Y+ I
1)Label【required】
% G4 }8 _. e3 f# K
; o. m: @. @$ X3 u) G) e/ v/ M该项服务的名称。
9 R9 t5 |2 H; X, q7 V: x* \4 F  Z0 Q+ v) |" Y  _1 ~# B8 e: c
2)OnDemand【optional】
& l9 q5 |0 p+ S8 t, R8 i6 w
7 Y7 p+ `- P8 x5 p* Z- Q1 B; v10.4提供的一个key值,功能与KeepAlive的基本功能相似,在10.5及之后的系统中被KeepAlive替代。KeepAlive扩展了更多的功能,除了使用单一的boolean作为key值之外,还能使用字典结合多个key值。! ~* d* T" h" ]

, ]$ n7 J" e0 P* i+ ?/ L" y7 y; V3)Program【ProgramArgument是required的,在没有ProgramArgument的情况下,必须要包含Program这个key】/ ]2 ]: r4 z- |6 e8 a! h' |, r( s

7 _* h- p4 |$ q' B4 F* e* j: ^指定可执行文件的路径。
0 |! F" F  s! @6 t* z8 @; O: O7 N1 g' c( V; B4 X9 X
4)RunAtLoad【optional】  R1 o5 K1 c+ e! i) A  h
: D" f. e- Y/ _: r5 p' n9 V
标识launchd在加载完该项服务之后立即启动路径指定的可执行文件。默认值为false。
: K# ]3 `, g$ w' W
. `! }) i) w0 X' ~5)WorkingDirectory【optional】' b$ ?8 E' c( j" E& b& Y; n

. z2 [, j" g) P( b$ N+ m4 X该key在开启可执行文件之前,指定当前工作目录的路径。
7 H% {2 F! p7 C: A
) j/ R8 \9 ~5 d% n4 g& ^6)KeepAlive【optional】
9 r- r# U% G# f1 M) n6 ?) S0 _9 v* G" ?" q* w3 }+ ^# z6 W- G
这个key值是用来控制可执行文件是持续运行呢,还是满足具体条件之后再启动。默认值为false,也就是说满足具体条件之后才启动。当设置值为ture时,表明无条件的开启可执行文件,并使之保持在整个系统运行周期内。
" |% h! r3 W4 X1 L. ~: z: C$ u$ `+ M1 H! }
3.2 创建一个plist文件:
+ @8 `  {; ?1 j$ y* k3 A! a<?xml version="1.0" encoding="UTF-8"?>
- j- C4 u- F+ O+ R5 s' Y$ M<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN"   ~! j+ L+ U0 V7 K1 D/ P
    "http://www.apple.com/DTDs/PropertyList-1.0.dtd">+ H# x1 ]+ a% [9 ~7 S
<plist version="1.0">. C3 U" k% i" U$ q! k. D
<dict>/ Z8 |6 w. P1 Z$ l( _- a; x6 f
    <key>Label</key>
! X) q0 O0 o; `& P) @. z. C        <string>com.yourcompany.HSPA_USB_MODEM</string>9 n2 c; Q4 s. S  G5 m" Z
    <key>OnDemand</key>- \9 c* g" ?" f/ [+ z, I! o& g
        <false/>1 @9 d; p0 d3 G! l1 p. @
    <key>Program</key>2 P" g  K0 G7 \" D$ u" H* B4 }
        <string>/Application/HSPA USB MODEM.app/Running</string>8 S* S0 Q/ @0 U' l3 u
    <key>RunAtLoad</key>
6 R8 h( y9 k4 K( T  U# a0 l' r( v        <true/># O& R; Q4 W" m' a: P5 J2 g
    <key>WorkingDirectory</key>
2 a5 i: o8 S& K' B1 B0 F9 q/ i2 s        <string>/Application/HSPA USB MODEM.app</string>' q% t" a8 n3 B$ v0 t) t) @
</dict>" h2 F8 \5 F- h, Y
</plist>
+ J8 Q( U7 r& r0 @7 n4.三种方式的区别
& ]5 m$ P4 V3 v" q初步了解了系统的启动过程之后,再来看这三种配置启动项的方式,就很容易理解这三种方式之间的差异了。/ K3 D7 Y9 S, o- F# L

* B0 D+ o5 E+ c总的来说,LoginItems 和StartupItems的区别较明显。
" L( E4 e$ M  h2 b9 R: w! N6 ]" `# O3 n0 S
- k% ]5 ?4 M9 s8 C2 w* _$ Y/ A
对于我们自定义的Launchd daemon,通常(同时也是系统推荐)是放在~/Library/LaunchAgents路径下。launchd进程需要在用户login之后才能加载。这种方式与LoginItems最大的区别在于,启动的进程不同。LoginItems是通过loginwindow去启动的,而Launchd daemon是通过com.apple.launchd.peruser启动。: U: u6 l% G% ]. Z- I6 s4 F
快手ID:ChinaFAQ-CN
QQ:25338
微信(WeChat):25338

QQ群:874864634
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|Archiver|手机版|小黑屋|ChinaFAQ论坛

GMT+8, 2025-12-2 03:57 , Processed in 0.054015 second(s), 20 queries .

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表