( ! ) Deprecated: Function WP_Dependencies-&gt;add_data() was called with an argument that is <strong>deprecated</strong> since version 6.9.0! IE conditional comments are ignored by all supported browsers. in /var/www/html/wp-includes/functions.php on line 6131
Call Stack
#TimeMemoryFunctionLocation
10.0000484224{main}( ).../index.php:0
20.0000484576require( '/var/www/html/wp-blog-header.php ).../index.php:17
30.11034299504require_once( '/var/www/html/wp-includes/template-loader.php ).../wp-blog-header.php:19
40.11164328824include( '/var/www/html/wp-content/themes/twentyfifteen/archive.php ).../template-loader.php:125
50.11164328824get_header( $name = ???, $args = ??? ).../archive.php:19
60.11164329040locate_template( $template_names = [0 => 'header.php'], $load = TRUE, $load_once = TRUE, $args = [] ).../general-template.php:48
70.11164329136load_template( $_template_file = '/var/www/html/wp-content/themes/twentyfifteen/header.php', $load_once = TRUE, $args = [] ).../template.php:749
80.11164329680require_once( '/var/www/html/wp-content/themes/twentyfifteen/header.php ).../template.php:814
90.11194337088wp_head( ).../header.php:18
100.11194337088do_action( $hook_name = 'wp_head' ).../general-template.php:3197
110.11194337304WP_Hook->do_action( $args = [0 => ''] ).../plugin.php:522
120.11194337304WP_Hook->apply_filters( $value = '', $args = [0 => ''] ).../class-wp-hook.php:365
130.11224340288wp_enqueue_scripts( '' ).../class-wp-hook.php:341
140.11224340288do_action( $hook_name = 'wp_enqueue_scripts' ).../script-loader.php:2311
150.11224340504WP_Hook->do_action( $args = [0 => ''] ).../plugin.php:522
160.11224340504WP_Hook->apply_filters( $value = '', $args = [0 => ''] ).../class-wp-hook.php:365
170.11244342392twentyfifteen_scripts( '' ).../class-wp-hook.php:341
180.11274343912wp_style_add_data( $handle = 'twentyfifteen-ie', $key = 'conditional', $value = 'lt IE 9' ).../functions.php:440
190.11274343912WP_Styles->add_data( $handle = 'twentyfifteen-ie', $key = 'conditional', $value = 'lt IE 9' ).../functions.wp-styles.php:245
200.11274343912WP_Dependencies->add_data( $handle = 'twentyfifteen-ie', $key = 'conditional', $value = 'lt IE 9' ).../class-wp-styles.php:385
210.11274462696_deprecated_argument( $function_name = 'WP_Dependencies->add_data()', $version = '6.9.0', $message = 'IE conditional comments are ignored by all supported browsers.' ).../class-wp-dependencies.php:317
220.11274468648wp_trigger_error( $function_name = '', $message = 'Function WP_Dependencies->add_data() was called with an argument that is <strong>deprecated</strong> since version 6.9.0! IE conditional comments are ignored by all supported browsers.', $error_level = 16384 ).../functions.php:5925
230.11284469400trigger_error( $message = 'Function WP_Dependencies-&gt;add_data() was called with an argument that is <strong>deprecated</strong> since version 6.9.0! IE conditional comments are ignored by all supported browsers.', $error_level = 16384 ).../functions.php:6131

( ! ) Deprecated: Function WP_Dependencies-&gt;add_data() was called with an argument that is <strong>deprecated</strong> since version 6.9.0! IE conditional comments are ignored by all supported browsers. in /var/www/html/wp-includes/functions.php on line 6131
Call Stack
#TimeMemoryFunctionLocation
10.0000484224{main}( ).../index.php:0
20.0000484576require( '/var/www/html/wp-blog-header.php ).../index.php:17
30.11034299504require_once( '/var/www/html/wp-includes/template-loader.php ).../wp-blog-header.php:19
40.11164328824include( '/var/www/html/wp-content/themes/twentyfifteen/archive.php ).../template-loader.php:125
50.11164328824get_header( $name = ???, $args = ??? ).../archive.php:19
60.11164329040locate_template( $template_names = [0 => 'header.php'], $load = TRUE, $load_once = TRUE, $args = [] ).../general-template.php:48
70.11164329136load_template( $_template_file = '/var/www/html/wp-content/themes/twentyfifteen/header.php', $load_once = TRUE, $args = [] ).../template.php:749
80.11164329680require_once( '/var/www/html/wp-content/themes/twentyfifteen/header.php ).../template.php:814
90.11194337088wp_head( ).../header.php:18
100.11194337088do_action( $hook_name = 'wp_head' ).../general-template.php:3197
110.11194337304WP_Hook->do_action( $args = [0 => ''] ).../plugin.php:522
120.11194337304WP_Hook->apply_filters( $value = '', $args = [0 => ''] ).../class-wp-hook.php:365
130.11224340288wp_enqueue_scripts( '' ).../class-wp-hook.php:341
140.11224340288do_action( $hook_name = 'wp_enqueue_scripts' ).../script-loader.php:2311
150.11224340504WP_Hook->do_action( $args = [0 => ''] ).../plugin.php:522
160.11224340504WP_Hook->apply_filters( $value = '', $args = [0 => ''] ).../class-wp-hook.php:365
170.11244342392twentyfifteen_scripts( '' ).../class-wp-hook.php:341
180.14144470504wp_style_add_data( $handle = 'twentyfifteen-ie7', $key = 'conditional', $value = 'lt IE 8' ).../functions.php:444
190.14144470504WP_Styles->add_data( $handle = 'twentyfifteen-ie7', $key = 'conditional', $value = 'lt IE 8' ).../functions.wp-styles.php:245
200.14144470504WP_Dependencies->add_data( $handle = 'twentyfifteen-ie7', $key = 'conditional', $value = 'lt IE 8' ).../class-wp-styles.php:385
210.14144470504_deprecated_argument( $function_name = 'WP_Dependencies->add_data()', $version = '6.9.0', $message = 'IE conditional comments are ignored by all supported browsers.' ).../class-wp-dependencies.php:317
220.14144470824wp_trigger_error( $function_name = '', $message = 'Function WP_Dependencies->add_data() was called with an argument that is <strong>deprecated</strong> since version 6.9.0! IE conditional comments are ignored by all supported browsers.', $error_level = 16384 ).../functions.php:5925
230.14154471048trigger_error( $message = 'Function WP_Dependencies-&gt;add_data() was called with an argument that is <strong>deprecated</strong> since version 6.9.0! IE conditional comments are ignored by all supported browsers.', $error_level = 16384 ).../functions.php:6131

Jetpack Mission 口香糖人的拯救任務

Jetpack Mission 口香糖人的拯救任務

軟體:Jetpack Mission(版本:N/A)
類別:動作遊戲
性質:Freeware()

【編輯/宗文】

遊戲中玩家必須藉由角度的調整,以及力量大小的決定來讓我們的主角往目的地前進。有時目的地會在前方,有時候又會在正上方,因此如何調整將是玩家要傷腦筋的地方。一但調整正確便能站上目的地,如果碰到目的地邊邊的話,主角還會有攀爬的方式上去,若是偏差太多就會看到可憐的主角掉到畫面外囉!

遊戲中有許多關卡,每個關卡的背景都不同,讓遊戲內容更加豐富。而每個關卡的目的地也都不同,例如第一關是西瓜,玩家必須讓主角能依序順利站上這些大小不同的西瓜。而除了一般西瓜之外,有些西瓜在一段時間後可是會破裂的,這常常會讓人緊張兮兮,因為調整的動作要很快,才不會讓主角從破裂的西瓜掉落。另外有些西瓜會間隔一段時間長出刺,玩家必須掌握不長刺的時間差來站上西瓜。




遊戲操控方面,利用滑鼠來決定主角跳躍的方向、角度與力量,只要移動滑鼠可以看到主角旁邊的雷達上會有長條線條的顯示,線條愈長主角可以跳得遠,線條愈陡表示角度愈大。遊戲畫面上方有一些指示訊息,有左至右分別是目前的關卡數、生命值、煞車裝置可用次數、加速能量多寡與分數。

在煞車裝置方面,當玩家覺得力量或角度沒調好,主角會越過目的地,此時可以按空白鍵,讓主角急停。相反的如果會在目的地前掉落,可以按住滑鼠左鍵不放來啟動加速系統。不過這兩項都會有使用的數量限制,因此要小心使用。另外站在平台上時,可以利用方向鍵中的左右鍵來移動主角。


下載:http://www.candystand.com/play.do?id=17983

Bomb It 炸彈機器人

Bomb It 炸彈機器人

軟體:Bomb It(版本:N/A)
類別:動作遊戲
性質:Freeware()

【編輯/宗文】

遊戲的玩法類似炸彈超人,都是利用炸彈來炸開周邊障礙物與攻擊對手。遊戲中有三種困難度與四個人物供玩家選擇,玩家可以挑選自己喜歡的人物進行遊戲,困難度方面則可以從簡單的開始挑戰。另外遊戲除了可一人獨玩外,也可以兩人一起加入競爭。遊戲中提供了多種場景,讓遊戲內容更加豐富更有變化。



遊戲中玩家要獲取勝利有兩種方式,第一種是擊敗所有對手,第二種是限制時間已到,還有對手未消滅的話,此時則會取分數最高的為優勝。遊戲中提供了多種寶物,例如增加可放置炸彈的數量、可以丟擲到遠方的炸藥、可以增加走路速度的鞋子與可以保護己身的防護盾等等,非常的豐富,善用這些寶物的話,對於攻擊對手而取得勝利會有很大的幫助。




遊戲操控說明:
1.獨自一人玩時:利用四個方向鍵移動主角,空白鍵可放置炸彈。
2.兩人玩時:
第一組按鍵:利用W、A、S、D四鍵移動主角,空白鍵放置炸彈。
第二組按鍵:利用四個方向鍵移動主角,Enter鍵可放置炸彈。

下載:

Dead Tree Defender 三箭客

Dead Tree Defender 三箭客

軟體:Dead Tree Defender(版本:N/A)
類別:射擊遊戲
性質:Freeware()

【編輯/宗文】

遊戲中玩家必須在每個關卡中,將所有的敵人消滅才能順利過關。遊戲有三種困難度可選擇,愈困難的關卡,其防禦工事做的更好,是很難用箭射中的,因此可以考驗玩家射擊的技術。每一關敵人的剩餘數量與總殲滅的敵人數量都會標示於畫面下方,玩家可以參考。



遊戲中除了有玩家可以控制的主角之外,還有兩名隊友可以支援玩家,不同這兩名隊友是會自己射擊,玩家無法控制。玩家所控制的主角可以任意移動,而且可以藉由跳躍或蹲下來躲避敵方攻擊,其他兩名隊友只能射擊不能移動。遊戲中我方的三名射手前方會有一木牆,這是我方的防禦工事。敵方會不斷利用各種不同的攻擊方式來攻擊我方,例如蛇人會丟出可怕的蛇,會丟擲石頭的敵人或射箭手等等,玩家必須利用準確的射擊來擊潰對手。

遊戲操控說明:
1.方向鍵的上鍵可以攀爬樓梯或跳躍。
2.方向鍵的下鍵可以爬下樓梯或蹲下。
3.方向鍵中的左右鍵可以移動主角。
4.利用滑鼠移動來控制射擊角度,按滑鼠左鍵可以射擊,按住愈久再放開可以射的更遠。

下載:http://www.crazymonkeygames.com/Dead-Tree-Defender.html

Crystal Mines 採水晶礦

Crystal Mines 採水晶礦

軟體:Crystal Mines(版本:N/A)
類別:益智遊戲
性質:Freeware()

【編輯/宗文】

這是一款益智遊戲,玩法有些類似倉庫番,都是要將物品推至定點。遊戲畫面中會出現許多種不同的水晶,玩家必須將這些水晶推動到紅色的箱子中,當箱子裝上水晶後就會消失,直到全部箱子都消失後,出口處才會打開,玩家到達出口處後才算過關。遊戲畫面的右上角有一個時鐘,玩家如能愈早完成關卡,則可以獲得的時間加分將會愈多。畫面左上角的紅心圖示則代表擁有的生命值,當玩家無法過關用滑鼠左鍵點擊「RESTAT LEVEL」時,可以重玩本關卡,但是會扣一點生命值。

遊戲中玩家一次只能推動一個水晶,因此如有兩個以上的水晶相接,一次是無法推動兩個以上水晶的。另外遊戲中會出現一些綠色植物或是石頭,綠色植物可被主角摘除,石頭只能推開不能去除,這些障礙物玩家要小心去除,以免檔到推動水晶行進的方向。遊戲中要小心不可把水晶推到牆壁角落,否則水晶可是無法再推動的。




遊戲操控方面,利用四個方向鍵移動主角,以及推動水晶。在過關後按空白鍵可以迅速跳過計分的畫面。

下載:

Evil Elves 2 偷竊聖誕禮物的小鬼2

Evil Elves 2 偷竊聖誕禮物的小鬼2

軟體:Evil Elves 2(版本:N/A)
類別:動作遊戲
性質:Freeware()

【編輯/宗文】

這是一款動作遊戲,由於有一羣邪惡小鬼偷走禮物,聖誕老人要將禮物找回。因此玩家必須幫忙聖誕老人在關卡中找尋所有的禮物,並且最後坐上雪橇才能順利過關。遊戲中的畫面色彩豐富,敵人的種類很多,每個關卡的風格變化很大,讓人不會感覺單調,這方面的表現很不錯。



每個關卡的敵人很多,種類也都不一樣,其攻擊招式變化萬千,所以玩家要非常注意,尤其一些速度快或者攻擊武器的範圍廣的。另外要注意地面上或牆上是否有機關或危險物品,才不會被扣生命點數。遊戲中玩家可以丟擲雪球來攻擊敵人,但是雪球的數量是有限制的,因此一些敵人如能避開,有時候並不需要將所有的敵人殲滅。



遊戲中會出現一些聖誕老人的頭像圖示或者雪球圖示,如果玩家能取得可以補充生命點數,如果能取得雪球圖示則可以補充可丟擲雪球的數量。遊戲中玩家如能愈早完成關卡,則可以獲得的時間加分將會愈多,而過關後的生命點數愈多,也可以獲得更多的加分。




遊戲操控說明:
1.利用方向鍵中的左右鍵移動主角。
2.方向鍵中的上鍵可以向上飛行,下鍵可以蹲下。
3.空白鍵可以丟擲雪球。

下載:

Flames of Fury 狂怒的火焰

Flames of Fury 狂怒的火焰

軟體:Flames of Fury(版本:N/A)
類別:射擊遊戲
性質:Freeware()

【編輯/宗文】

這是一款射擊遊戲,玩家必須帶領飛龍來消滅敵人,相對的敵人也會派出大量軍隊來攻擊飛龍巢穴,玩家必須防禦它,一旦巢穴被擊毀,遊戲就會結束。遊戲中有三種困難度,建議玩家從簡單的開始挑戰,熟悉遊戲後再挑戰困難的。飛龍的巢穴可以製造各種火球,與防禦火焰(阻擋敵人直接攻擊飛龍巢穴),如有升級點數也可以在巢穴中升級各種不同飛龍的能力,另外也可以利用資源來恢復健康值。



飛龍可以發射各種不同類型的火球,不過這些火球必須有兩種資源才能製造(飛龍靠近這兩種資源提供處便能取得。),一種是藍色的氫資源,一種是紅色的硫磺資源,玩家必須尋找這兩資源,然後再回到巢穴中來合成火球。各種火球的攻擊值與消耗能源的數量都不同,端看玩家如何來做出最佳抉擇。在這個過程中敵人會不斷騷擾飛龍,以及攻擊其巢穴,所以一旦發現敵軍要攻擊巢穴時,記得趕緊回防。另外要注意這兩種資源可是會用完的,因此玩家在攻擊敵人方面要力求準確,否則能源用完時可就無法再攻擊敵人了。



在敵人方面有分為數種,底下介紹幾個敵軍的種類或建築物。一種是陸上的裝甲車,它無法攻擊我方基地,只能在一定範圍內移動攻擊飛龍。戰鬥直昇機可以靠近飛龍巢穴並攻擊它,所以一但看到戰鬥直昇機應該先摧毀它。另外還有敵軍的防禦塔,以及生產戰鬥單位的兵工廠,都是玩家要攻擊的目標。遊戲操控說明:1.利用四個方向鍵移動飛龍。2.滑鼠移動可以瞄準敵人,按滑鼠左鍵可以發射火球。3.按空白鍵可以改變火球類型。

下載:

Spikey’s Bounce Around 史碧奇解救蝴蝶冒險記

Spikey’s Bounce Around 史碧奇解救蝴蝶冒險記

軟體:Spikey’s Bounce Around(版本:N/A)
類別:動作遊戲
性質:Freeware()

【編輯/宗文】

遊戲中玩家必須引導主角,在關卡中透過打破玻璃瓶來解救被關住的蝴蝶,不過這可不簡單喔!因為除了主角的彈跳次數有限制外,許多關卡中還藏有許多危機,以及有很多敵人來干擾玩家。遊戲中如果移動次數變為零而尚有蝴蝶未救出,遊戲就會結束。另外玩家如能減少移動次數而過關,將可以獲得額外的加分。遊戲的玩法非常簡單,玩家首先移動滑鼠來設定要行進的方向,然後按滑鼠左鍵主角便會移動,不過要注意主角移動的距離有所限制,玩家如要到達較遠目標,應該分次來行動。在每一個不同關卡中,玩家要將所有蝴蝶都救出來才能過關,如要打破玻璃瓶而救出蝴蝶的話,必須將支撐玻璃瓶的植物或樹藤去除,這些都將會消耗主角移動的次數,因此玩家必須算準才能減少主角移動的次數。



遊戲中還會出現一些彈跳物品,當主角碰到這些物品時會彈跳到其他地方,另外還有許多危險物品及敵人出現,玩家要算準時間差或跳躍的角度來避開他們,否則一碰觸可是會扣能量值的。

下載:

Summary of regular-expression constructs


Summary of regular-expression constructs































































































































































































































































































































Construct Matches
 
Characters
x The character x
\\ The backslash character
\0n The character with octal value 0n (0 <= n <= 7)
\0nn The character with octal value 0nn (0 <= n <= 7)
\0mnn The character with octal value 0mnn (0 <= m <= 3, 0 <= n <= 7)
\xhh The character with hexadecimal value 0xhh
\uhhhh The character with hexadecimal value 0xhhhh
\t The tab character (‘\u0009’)
\n The newline (line feed) character (‘\u000A’)
\r The carriage-return character (‘\u000D’)
\f The form-feed character (‘\u000C’)
\a The alert (bell) character (‘\u0007’)
\e The escape character (‘\u001B’)
\cx The control character corresponding to x
 
Character classes
[abc] a, b, or c (simple class)
[^abc] Any character except a, b, or c (negation)
[a-zA-Z] a through z or A through Z, inclusive (range)
[a-d[m-p]] a through d, or m through p: [a-dm-p] (union)
[a-z&&[def]] d, e, or f (intersection)
[a-z&&[^bc]] a through z, except for b and c: [ad-z] (subtraction)
[a-z&&[^m-p]] a through z, and not m through p: [a-lq-z](subtraction)
 
Predefined character classes
. Any character (may or may not match line terminators)
\d A digit: [0-9]
\D A non-digit: [^0-9]
\s A whitespace character: [ \t\n\x0B\f\r]
\S A non-whitespace character: [^\s]
\w A word character: [a-zA-Z_0-9]
\W A non-word character: [^\w]
 
POSIX character classes (US-ASCII only)
\p{Lower} A lower-case alphabetic character: [a-z]
\p{Upper} An upper-case alphabetic character:[A-Z]
\p{ASCII} All ASCII:[\x00-\x7F]
\p{Alpha} An alphabetic character:[\p{Lower}\p{Upper}]
\p{Digit} A decimal digit: [0-9]
\p{Alnum} An alphanumeric character:[\p{Alpha}\p{Digit}]
\p{Punct} Punctuation: One of !”#$%&'()*+,-./:;<=>?@[\]^_`{|}~
\p{Graph} A visible character: [\p{Alnum}\p{Punct}]
\p{Print} A printable character: [\p{Graph}]
\p{Blank} A space or a tab: [ \t]
\p{Cntrl} A control character: [\x00-\x1F\x7F]
\p{XDigit} A hexadecimal digit: [0-9a-fA-F]
\p{Space} A whitespace character: [ \t\n\x0B\f\r]
 
Classes for Unicode blocks and categories
\p{InGreek} A character in the Greek block (simple block)
\p{Lu} An uppercase letter (simple category)
\p{Sc} A currency symbol
\P{InGreek} Any character except one in the Greek block (negation)
[\p{L}&&[^\p{Lu}]]  Any letter except an uppercase letter (subtraction)
 
Boundary matchers
^ The beginning of a line
$ The end of a line
\b A word boundary
\B A non-word boundary
\A The beginning of the input
\G The end of the previous match
\Z The end of the input but for the final terminator, if any
\z The end of the input
 
Greedy quantifiers
X? X, once or not at all
X* X, zero or more times
X+ X, one or more times
X{n} X, exactly n times
X{n,} X, at least n times
X{n,m} X, at least n but not more than m times
 
Reluctant quantifiers
X?? X, once or not at all
X*? X, zero or more times
X+? X, one or more times
X{n}? X, exactly n times
X{n,}? X, at least n times
X{n,m}? X, at least n but not more than m times
 
Possessive quantifiers
X?+ X, once or not at all
X*+ X, zero or more times
X++ X, one or more times
X{n}+ X, exactly n times
X{n,}+ X, at least n times
X{n,m}+ X, at least n but not more than m times
 
Logical operators
XY X followed by Y
X|Y Either X or Y
(X) X, as a capturing group
 
Back references
\n Whatever the nth capturing group matched
 
Quotation
\ Nothing, but quotes the following character
\Q Nothing, but quotes all characters until \E
\E Nothing, but ends quoting started by \Q
 
Special constructs (non-capturing)
(?:X) X, as a non-capturing group
(?idmsux-idmsux)  Nothing, but turns match flags on – off
(?idmsux-idmsux:X)   X, as a non-capturing group with the given flags on – off
(?=X) X, via zero-width positive lookahead
(?!X) X, via zero-width negative lookahead
(?<=X) X, via zero-width positive lookbehind
(?<!X) X, via zero-width negative lookbehind
(?>X) X, as an independent, non-capturing group




Backslashes, escapes, and quoting


The backslash character (‘\’) serves to introduce escaped constructs, as defined in the table above, as well as to quote characters that otherwise would be interpreted as unescaped constructs. Thus the expression \\ matches a single backslash and \{ matches a left brace.

It is an error to use a backslash prior to any alphabetic character that does not denote an escaped construct; these are reserved for future extensions to the regular-expression language. A backslash may be used prior to a non-alphabetic character regardless of whether that character is part of an unescaped construct.

Backslashes within string literals in Java source code are interpreted as required by the Java Language Specification as either Unicode escapes or other character escapes. It is therefore necessary to double backslashes in string literals that represent regular expressions to protect them from interpretation by the Java bytecode compiler. The string literal “\b”, for example, matches a single backspace character when interpreted as a regular expression, while “\\b” matches a word boundary. The string literal “\(hello\)” is illegal and leads to a compile-time error; in order to match the string (hello) the string literal “\\(hello\\)” must be used.

Character Classes


Character classes may appear within other character classes, and may be composed by the union operator (implicit) and the intersection operator (&&). The union operator denotes a class that contains every character that is in at least one of its operand classes. The intersection operator denotes a class that contains every character that is in both of its operand classes.

The precedence of character-class operators is as follows, from highest to lowest:























1     Literal escape     \x
2     Grouping […]
3     Range a-z
4     Union [a-e][i-u]
5     Intersection [a-z&&[aeiou]]

Note that a different set of metacharacters are in effect inside a character class than outside a character class. For instance, the regular expression . loses its special meaning inside a character class, while the expression becomes a range forming metacharacter.

Line terminators


A line terminator is a one- or two-character sequence that marks the end of a line of the input character sequence. The following are recognized as line terminators:


  • A newline (line feed) character (‘\n’),
  • A carriage-return character followed immediately by a newline character (“\r\n”),
  • A standalone carriage-return character (‘\r’),
  • A next-line character (‘\u0085’),
  • A line-separator character (‘\u2028’), or
  • A paragraph-separator character (‘\u2029).

If UNIX_LINES mode is activated, then the only line terminators recognized are newline characters.

The regular expression . matches any character except a line terminator unless the DOTALL flag is specified.

By default, the regular expressions ^ and $ ignore line terminators and only match at the beginning and the end, respectively, of the entire input sequence. If MULTILINE mode is activated then ^ matches at the beginning of input and after any line terminator except at the end of input. When in MULTILINE mode $ matches just before a line terminator or the end of the input sequence.

Groups and capturing


Capturing groups are numbered by counting their opening parentheses from left to right. In the expression ((A)(B(C))), for example, there are four such groups:
















1     ((A)(B(C)))
2     (A)
3     (B(C))
4     (C)

Group zero always stands for the entire expression.

Capturing groups are so named because, during a match, each subsequence of the input sequence that matches such a group is saved. The captured subsequence may be used later in the expression, via a back reference, and may also be retrieved from the matcher once the match operation is complete.

The captured input associated with a group is always the subsequence that the group most recently matched. If a group is evaluated a second time because of quantification then its previously-captured value, if any, will be retained if the second evaluation fails. Matching the string “aba” against the expression (a(b)?)+, for example, leaves group two set to “b”. All captured input is discarded at the beginning of each match.

Groups beginning with (? are pure, non-capturing groups that do not capture text and do not count towards the group total.

Unicode support


This class follows Unicode Technical Report #18: Unicode Regular Expression Guidelines, implementing its second level of support though with a slightly different concrete syntax.

Unicode escape sequences such as \u2014 in Java source code are processed as described in ?3.3 of the Java Language Specification. Such escape sequences are also implemented directly by the regular-expression parser so that Unicode escapes can be used in expressions that are read from files or from the keyboard. Thus the strings “\u2014” and “\\u2014”, while not equal, compile into the same pattern, which matches the character with hexadecimal value 0x2014.

Unicode blocks and categories are written with the \p and \P constructs as in Perl. \p{prop} matches if the input has the property prop, while \P{prop} does not match if the input has that property. Blocks are specified with the prefix In, as in InMongolian. Categories may be specified with the optional prefix Is: Both \p{L} and \p{IsL} denote the category of Unicode letters. Blocks and categories can be used both inside and outside of a character class.

The supported blocks and categories are those of The Unicode Standard, Version 3.0. The block names are those defined in Chapter 14 and in the file Blocks-3.txt of the Unicode Character Database except that the spaces are removed; “Basic Latin”, for example, becomes “BasicLatin”. The category names are those defined in table 4-5 of the Standard (p. 88), both normative and informative.

Comparison to Perl 5


Perl constructs not supported by this class:




  • The conditional constructs (?{X}) and (?(condition)X|Y),



  • The embedded code constructs (?{code}) and (??{code}),



  • The embedded comment syntax (?#comment), and



  • The preprocessing operations \l \u, \L, and \U.


Constructs supported by this class but not by Perl:




  • Possessive quantifiers, which greedily match as much as they can and do not back off, even when doing so would allow the overall match to succeed.



  • Character-class union and intersection as described above.


Notable differences from Perl:




  • In Perl, \1 through \9 are always interpreted as back references; a backslash-escaped number greater than 9 is treated as a back reference if at least that many subexpressions exist, otherwise it is interpreted, if possible, as an octal escape. In this class octal escapes must always begin with a zero. In this class, \1 through \9 are always interpreted as back references, and a larger number is accepted as a back reference if at least that many subexpressions exist at that point in the regular expression, otherwise the parser will drop digits until the number is smaller or equal to the existing number of groups or it is one digit.



  • Perl uses the g flag to request a match that resumes where the last match left off. This functionality is provided implicitly by the Matcher class: Repeated invocations of the find method will resume where the last match left off, unless the matcher is reset.



  • In Perl, embedded flags at the top level of an expression affect the whole expression. In this class, embedded flags always take effect at the point at which they appear, whether they are at the top level or within a group; in the latter case, flags are restored at the end of the group just as in Perl.



  • Perl is forgiving about malformed matching constructs, as in the expression *a, as well as dangling brackets, as in the expression abc], and treats them as literals. This class also accepts dangling brackets but is strict about dangling metacharacters like +, ? and *, and will throw a PatternSyntaxException if it encounters them.


For a more precise description of the behavior of regular expression constructs, please see Mastering Regular Expressions, 2nd Edition, Jeffrey E. F. Friedl, O’Reilly and Associates, 2002.

Hacking initrd.img – 添加网卡驱动,网络安装 Linux

如何在initrd.img中添加驱动


2007 年 9 月 20 日


本文通过将网卡驱动加入到 initrd.img 中,使 Linux 内核在启动的过程中能正确识别并加载网卡驱动,从而使网络安装得以进行。

前言


网络安装 Linux 并不是一个新鲜的话题,其过程也不是一个轻松的体验。为了让机器能通过网络来安装 Linux,如果还需要配合 kickstart 来自动化 Linux 的安装过程的话,用户需要做大量的配置工作。众所周知,用户需要挑选一台机器作为服务器,然后在这台机器上配置 DHCP, TFTP, NFS/Http/Ftp, pxelinux, kickstart 等一系列的东西。


但是所有的这一切能成功运作都至少有一个前提条件:我们所安装的 Linux 能正确的识别并驱动所有客户机的网卡。如果网卡驱动不了,客户机根本无法通过网络从服务器取到所需要的东西,网络安装 Linux 就无从谈起了。


本文通过将网卡驱动加入到 initrd.img 中,使 Linux 内核在启动的过程中能正确识别并加载网卡驱动,从而使网络安装得以进行。本文并不讲述网络安装 Linux 的背景知识(如为什么需要网络安装,网络安装的好处等)、具体配置和操作步骤(也就是配置 DHCP,TFTP,pxelinux 等内容)。此外,本文需要读者有熟练的 Linux 操作经验和 Shell 编程的基本知识,而且对 Linux 启动过程和驱动程序有基本的了解。


注:所有被安装的机器我们称之为客户机,提供网络安装服务的机器我们称之为服务器





















开始之前的建议


建议:如果您碰到了前言中所描述的问题的话,最好的解决方法是 – 找一个能驱动客户机网卡的 Linux Distribution,这样能省却很多麻烦。


但在现实环境下,很多原因会导致我们无法选择安装一个新的 Linux 发行版。原因有很多,比如:



  • 客户不同意我们选用其他的 Linux 版本,因为客户有大量的应用程序已经在某个Linux 版本上编译,运行良好了,更换 Linux 发行版会带来应用的移植问题
  • 客户拥有一些特殊的硬件,而这些硬件只有基于某个 Linux 发行版的驱动。更换 Linux 发行版,会导致这些硬件无法正常工作
  • 没有一个 Linux 发行版能驱动客户机的网卡。网卡厂商只给我们提供了某个 Linux 发行版上的驱动,一切都要 DIY
  • 您有着强烈的DIY情感,面对问题不是寻求别人的解决方案而是一切都要自己克服 – 毫无疑问,您就是本文最适合的读者




















解决思路


如果熟悉 Linux 的启动过程和驱动程序,那么要解决本文的问题,基本上有两条路可走。第一就是将网卡驱动编译进内核(静态链接进内核),第二种方法就是将网卡驱动做成模块,然后想办法在 Linux 启动的时候让 Linux 内核能找到并挂载该驱动。面对这两种方案,第二种方法有更好的可行性和扩展性。因为首先有些网卡驱动本身就不能被静态链接进入内核,而只能被编译成一个模块,例如下文要举的例子 – e1000 网卡驱动;其次,驱动做成模块的方式,可以适应多个内核版本,用方法 1,更换一个内核版本就要重新编译一次内核;最后,等会会看到,相比编译内核,方法 2 更简单和可操作。


方法 2 的实现手段就是定制 initrd.img,将我们的网卡驱动加进去。initrd.img 是一个小型的根文件系统,在 Linux 内核没有挂载硬盘上的根分区的时候,initrd.img 将在内存中展开。一般情况下,initrd.img 中将包含一些必需的命令和驱动,如 insmod 命令和磁盘驱动。有了 insmod,才能将磁盘驱动挂载进内核,有了磁盘驱动,内核才能挂载位于磁盘上的根文件系统。


大部分的 Linux 发行版都提供了用于网络安装 Linux 的 initrd.img,一般位于第一张安装光盘的 images/pxeboot 目录下。在一台已经装好 Linux 的机器中,在 /boot 目录下我们也能找到 initrd.img,比较一下这两个 initrd.img,会发现 pxeboot 目录下的 initrd.img 会比 /boot 下的大很多,这是因为在网络安装的情况下,Linux 不会尝试去挂载位于磁盘上的根分区(事实上,在没有安装Linux的机器上,此时磁盘中可能什么数据都没有),所以此时的 initrd.img 需要包含大量的驱动,使 Linux 能识别大量的硬件。位于 /boot 下的 initrd.img,基本上唯一需要的东西就是磁盘驱动,只要内核能访问磁盘,那么其余所需的东西都可以从磁盘取得而不需要依赖 initrd.img。





















具体操作和实例


从安装光盘中取得 initrd.img 之后,就可以开始对其进行定制。这里要感谢 Jeremy Mates,他写的 initrd-util.sh 能很好的解开和生成一个 initrd.img。脚本可以在http://sial.org/howto/linux/initrd/initrd-util下载到。


下面我们以RedHat Enterprise Linux Advance Server 4 Update 2 x86_64,Intel e1000网卡驱动为例,讲述具体的操作过程(在本例中,服务器和客户机拥有相同的Intel e1000网卡,而且我们已经手动在服务器上安装完成了正确的e1000驱动):


首先从光盘取到initrd.img,登录到服务器,然后用initrd-util.sh解开:


命令输出 1. 解开initrd.img





[root@ericvm ~]# cd `./initrd-util.sh unpack initrd.img |tail -1`
info: initrd unpack expanded into: /var/tmp/initrd-util.workdir.DA29317
[root@ericvm initrd-util.workdir.DA29317]# pwd
/var/tmp/initrd-util.workdir.DA29317
[root@ericvm initrd-util.workdir.DA29317]# ls
2.6.9-22.EL bin dev etc linuxrc lost+found modules
proc sbin selinux sys tmp var


initrd-util.sh很简单,利用gunzip, mount和cpio这些工具将initrd.img解开,其中驱动包位于modules目录下,名为modules.cgz,将这个文件解开后,生成了2.6.9-22.EL目录,进入该目录,就能找到包含在initrd.img中的驱动。本例中,RedHat已经包含了一个e1000的驱动,但是这个驱动不能驱动我们新的Intel e1000网卡。为此,我们在e1000网站下载新版的驱动,然后在服务器上编译完成,生成ko模块文件,然后拷贝到2.6.9-22.EL目录下,覆盖原文件即可。


驱动更新完毕后,现在我们需要将2.6.9-22.EL这个目录重新制作成modules.cgz,这个功能initrd-util.sh不能为我们完成,所以我们手动操作:


命令输出 2. 加入驱动并重新打包





[root@ericvm initrd-util.workdir.DA29317]# find 2.6.9-22.EL | cpio -o -H crc > newmodules
16582 blocks
[root@ericvm initrd-util.workdir.DA29317]# gzip -n -9 newmodules
[root@ericvm initrd-util.workdir.DA29317]# mv newmodules.gz modules
[root@ericvm initrd-util.workdir.DA29317]# cd modules
[root@ericvm modules]# rm -f modules.cgz
[root@ericvm modules]# mv newmodules.gz modules.cgz
[root@ericvm modules]# pwd
/var/tmp/initrd-util.workdir.DA29317/modules


驱动包重新生成了并不意味着Linux就可以识别网卡了,因为Linux必须依靠一种逻辑,将硬件设备和驱动模块文件对应起来。这个逻辑就被定义在modules目录下的除modules.cgz之外的文件中:


命令输出 3. 设备驱动识别信息文件





[root@ericvm modules]# ls
module-info modules.cgz modules.dep modules.pcimap modules.usbmap pci.ids pcitable


如上所示,pcitable, modules.pcimap中定义了PCI设备和驱动模块之间的对应关系,modules.dep中定义了模块和模块之间的依赖关系(比如,各种SCSI设备都会依赖一个基础的SCSI驱动模块),module-info中定义了驱动的静态描述信息……


要填写这些文本文件,也很简单,首先我们必须要知道这块e1000网卡的PCI设备信息,由于在服务器上e1000这块网卡已经安装完成了,所以我们可以在服务器上取到我们想要的信息:


命令输出 4. 查看网卡硬件信息





[root@ericvm ~]# lspci
………… ignore some outputs
04:00.0 Ethernet controller: Intel Corporation Enterprise Southbridge DPT LAN Copper
04:00.1 Ethernet controller: Intel Corporation Enterprise Southbridge DPT LAN Copper
………… ignore some outputs


lspci列出了服务器上两块网卡的设备信息,根据网卡设备的ID号码(04:00.0, 04:00.1),我们就可以在lspci –n的输出中找到设备的vendor code和device code(请参考lspci的manual了解lspci):


命令输出 5. 查看网卡code





[root@ericvm ~]# lspci –n
………… ignore some outputs
04:00.0 Class 0200: 8086:1096 (rev 01)
04:00.1 Class 0200: 8086:1096 (rev 01)
………… ignore some outputs


在lspci –n的输出中,我们找到了两块网卡的vendor code和device code – 8086和1096。得到了vendor code和device code之后,就可以更新initrd.img中modules目录下的pcitable, modules.pcimap等这些文件了。举例来说,在pcitable中查找e1000,能发现很多设备和e1000这个驱动关联,但是唯独没有8086:1096的组合,这就是为什么Linux无法驱动这块e1000网卡的原因了,我们需要手动将8086, 1096这两个code加入到pcitable中,并将这个设备对应到e1000驱动上。照此方法,更新其余的文件,如module-info, modules.pcimap等。


这样我们就完成了对initrd.img的完全修改,用initrd-util.sh重新将目录打包,生成一个新的initrd.img:


命令输出 6. 重新生成initrd.img





[root@ericvm ~]# ./initrd-util.sh pack /var/tmp/initrd-util.workdir.DA29317/
notice: new initrd size: 6144K
6144+0 records in
6144+0 records out
mke2fs 1.35 (28-Feb-2004)
info: initrd packed into: /var/tmp/initrd-util.initrd-new.IV29439.gz
/var/tmp/initrd-util.initrd-new.IV29439.gz
[root@ericvm ~]# ls -lh /var/tmp
total 3.7M
-rw-r–r– 1 root root 3.7M Jun 20 17:10 initrd-util.initrd-new.IV29439.gz
drwxr-xr-x 12 root root 4.0K Jun 20 17:10 initrd-util.workdir.DA29317
drwxr-xr-x 13 root root 4.0K Jun 20 15:53 initrd-util.workdir.ID29288


initrd-util.sh首先创建一个“空洞文件”,然后在这个文件中建立ext2 文件系统,然后将这个文件mount到一个目录中,最后用rsync这种方式将我们更新过的文件“拷贝”到了mount的目录下,这样“空洞”文件中就有了内容,最后对文件进行压缩,生成最终的img文件。


将/var/tmp/initrd-util.initrd-new.IV29439.gz改名成initrd.img,放到tftp配置的目录下,就可以让客户机在网络启动的时候取到新的initrd.img了,从而识别网卡开始网络安装。





















到此为止了么?


到目前为止,一切看起来都很好。客户机通过网络启动,能把网卡驱动起来并从服务器上得到所有需要的东西,并开始安装。但是,如果没有做特殊处理的话,客户机上Linux安装完成后,启动进入Linux,会发现网卡依旧驱动不了,典型的出错信息就是“无法成功挂载XXX驱动”,“ethX的MAC地址和预计的不一样”等。出现这样问题的原因很简单,这是因为正确的网卡驱动只存在于服务器上的 initrd.img 中,而没有体现到客户机的硬盘上。客户机在网络启动的时候得到了服务器上的 initrd.img,但 Linux 还没有智能到能自动解开这个 initrd.img 并将里面的驱动拷贝到客户机的硬盘上。一旦客户机完成安装重启,从硬盘启动之后,所有的驱动文件和信息就都从硬盘读取了。


还举刚才的例子,e1000 网卡驱动在 RedHat 中其实自带就有一个,但不适用于我们的 Intel e1000 网卡,用 rpm 命令可以查到安装在硬盘上的这个 e1000 驱动属于哪个RPM包:


命令输出 7. 查看驱动所在的 RPM 包





# rpm -qf /lib/modules/2.6.9-42.ELsmp/kernel/drivers/net/e1000/e1000.ko
kernel-smp-2.6.9-42.EL


所以,很明显的就是,要解决这样的问题,我们需要重新生成这个 kernel RPM 包。但是要在 RPM 包中替换一个文件,或是加入一个文件,可不像在 RAR 文件中用鼠标直接拖拽那么简单。有兴趣的可以参考 RPM 的相关资料。


除了重新生成 RPM 之外,还有一些简单的办法也是可行的,但不如重新生成 RPM 来的中规中矩。有兴趣的读者可以和我交流,这里就不赘述了。




参考资料



 

Linux 技巧: 用 cron 和 at 调度作业

Linux 技巧: 用 cron 和 at 调度作业


如何轻松地管理系统



2007 年 8 月 27 日


系统管理员需要在系统负载低的午夜运行作业,或者需要每天或每月运行作业,同时又不愿意牺牲睡眠时间或假期。调度任务的其他原因包括自动执行日常任务或者确保每次都以相同的方式处理任务。本文帮助您使用 cronat 功能调度作业定期运行或在指定的时间运行一次。

Linux® 和 UNIX® 系统允许调度任务在以后执行一次,或者重复运行。本文是从 developerWorks 教程 “LPI 102 考试准备:管理任务” 摘录的,讲解如何调度作业定期运行,或在指定的时间运行一次。


在 Linux 系统上,许多管理任务必须频繁地定期执行。这些任务包括轮转日志文件以避免装满文件系统、备份数据和连接时间服务器来执行系统时间同步。上面提到的教程更详细地介绍了这些管理任务。在本文中,学习 Linux 中提供的调度机制,包括 cronanacron 设施以及 crontabat 命令。即使系统常常关机,anacron 也可以帮助调度作业。


以一定的时间间隔运行作业


以一定的时间间隔运行作业需要使用 cron 设施进行管理,它由 crond 守护进程和一组表(描述执行哪些操作和采用什么样的频率)组成。这个守护进程每分钟唤醒一次,并通过检查 crontab 判断需要做什么。用户使用 crontab 命令管理 crontab。crond 守护进程常常是在系统启动时由 init 进程启动的。


为了简单,假设希望定期运行清单 1 所示的命令。这个命令实际上只报告日期和时间,其他什么事都不做,但是它可以说明如何使用 crontab 设置 cron 作业,而且还可以通过输出看到作业运行的时间。设置 crontab 条目需要一个包含转义的 shell 元字符的字符串,所以适合于简单的命令和参数。在这个示例中,将从脚本 /home/ian/mycrontab.sh 运行 echo 命令,这个脚本不需要参数。 这可以减少处理转义字符的工作。


清单 1. 一个简单的命令示例





[ian@lyrebird ~]$ cat mycrontest.sh
#!/bin/bash
echo “It is now $(date +%T) on $(date +%A)”
[ian@lyrebird ~]$ ./mycrontest.sh
It is now 18:37:42 on Friday


创建 crontab


使用 crontab 命令和 -e(表示 “edit”)选项创建 crontab。这会打开 vi 编辑器,除非在 EDITOR 或 VISUAL 环境变量中指定了另一种编辑器。


每个 crontab 条目包含六个字段:



  1. 分钟
  2. 小时


  3. 星期
  4. sh 执行的字符串

分钟和小时的范围分别是 0-59 和 0-12,日和月的范围分别是 1-31 和 1-12。星期的范围是 0-6,0 表示星期日。星期也可以指定为 sun、mon、tue 等等。第 6 个字段包含前 5 个字段之后的所有内容,它是要传递给 sh 的字符串。百分号(%)将转换为空行,所以如果要使用 % 或其他任何特殊字符,就要在前面加上反斜线(\)。第一个 % 之前的一行传递给 shell,这个 % 之后的所有行都作为标准输入传递。


各个与时间相关的字段可以指定一个单独的值、值的范围(比如 0-10 或 sun-wed)或者以逗号分隔的单独值和范围列表。清单 2 给出一个 crontab 条目示例。


清单 2. 一个简单的 crontab 示例





0,20,40 22-23 * 7 fri-sat /home/ian/mycrontest.sh


在这个示例中,我们的命令在 7 月的每个星期五和星期六晚上 10 点到午夜之间的第 0、20、40 分钟(每 20 分钟)执行。关于指定时间的其他方式的细节,参见 crontab(5) 的手册页。


输出


您可能想知道对来自命令的输出会如何处理。为使用 cron 而设计的大多数命令会使用 syslog 在日志中记录输出(参见教程 “LPI 102 考试准备:管理任务” 中的讨论)。但是,定向到 stdout 的输出会通过电子邮件发送给用户。清单 3 给出我们的命令示例可能产生的输出。


清单 3. 通过电子邮件发送的 cron 输出





From [email protected] Fri Jul 6 23:00:02 2007
Date: Fri, 6 Jul 2007 23:00:01 -0400
From: [email protected] (Cron Daemon)
To: [email protected]
Subject: Cron <ian@lyrebird> /home/ian/mycrontest.sh
Content-Type: text/plain; charset=UTF-8
Auto-Submitted: auto-generated
X-Cron-Env: <SHELL=/bin/sh>
X-Cron-Env: <HOME=/home/ian>
X-Cron-Env: <PATH=/usr/bin:/bin>
X-Cron-Env: <LOGNAME=ian>
X-Cron-Env: <USER=ian>

It is now 23:00:01 on Friday



crontab 存储在哪里?










suid 程序

suid 程序以程序文件的所有者的权限运行,而不是采用运行程序的用户的权限。关于 suid 的更多信息,参见教程 “LPI 101 考试准备:设备、Linux 文件系统和 Filesystem Hierarchy Standard”;关于 passwd 命令的更多信息,参见教程 “LPI 102 考试准备:管理任务”。


crontab 命令创建的 crontab 存储在 /etc/spool/cron 下面的一个子目录中,这个子目录与创建 crontab 的用户同名,所以上面的 crontab 存储在 /etc/spool/cron/ian 中。因此,与 passwd 命令一样,crontab 命令是一个用根权限运行的 suid 程序。


/etc/crontab


除了 /var/spool/cron 中的用户 crontab 文件之外,cron 还会检查 /etc/crontab 文件和 /etc/cron.d 目录中的文件。在这些系统 crontab 中,在第五个时间字段(星期)和命令之间增加了一个字段。这个字段指定哪个用户应该运行这个命令,一般情况下是根用户。清单 4 给出一个 /etc/crontab 文件示例。


清单 4. /etc/crontab





SHELL=/bin/bash
PATH=/sbin:/bin:/usr/sbin:/usr/bin
MAILTO=root
HOME=/

# run-parts
01 * * * * root run-parts /etc/cron.hourly
02 4 * * * root run-parts /etc/cron.daily
22 4 * * 0 root run-parts /etc/cron.weekly
42 4 1 * * root run-parts /etc/cron.monthly



在这个示例中,真正的工作由 run-parts 命令执行,它运行 /etc/cron.hourly、/etc/cron.daily 等目录中的脚本;/etc/crontab 仅仅控制执行作业的时间。注意,这里的所有命令都作为根用户运行。还要注意,crontab 可以包含 shell 变量赋值,这些赋值会在运行命令之前执行。


anacron


cron 适合那些连续运行的系统。对于那些常常不开机的系统,比如笔记本计算机,可以使用另一个实用程序 anacron(表示 “anachronistic cron”)调度每日、每周或每月执行的作业。anacron 不处理每小时执行的作业。


anacron 在 /var/spool/anacron 中保留时间戳文件,记录作业运行的时间。当 anacron 运行时,它检查自作业上一次运行以来是否已经经过了所需的天数,如果需要,就运行作业。anacron 的作业表存储在 /etc/anacrontab 中,文件格式与 /etc/crontab 略有不同。与 /etc/crontab 一样,/etc/anacrontab 可以包含环境设置。每个作业有四个字段:



  1. 周期
  2. 延迟
  3. 作业标识符
  4. 命令

周期是天数,但是可以指定为 @monthly,这确保作业每个月只运行一次(无论这个月中有多少天)。延迟是在作业符合运行条件之后,到实际启动它之前等待的分钟数。可以使用这个设置防止在系统启动时集中执行作业。作业标识符可以包含除了斜线(/)之外的所有非空白字符。


/etc/crontab 和 /etc/anacrontab 都通过直接编辑进行更新。不使用 crontab 命令更新这些文件或 /etc/cron.d 目录中的文件。





















在指定的时间运行作业


有时候,需要只运行作业一次而不是定期运行。为此,应该使用 at 命令。要运行的命令是从 -f 选项指定的文件读取的,如果没有使用 -f,那么从 stdin 读取。-m 选项向用户发送邮件,即使命令没有 stdout。-v 选项显示运行作业的时间。这个时间也显示在输出中。


清单 5 给出一个运行 mycrontest.sh 脚本的示例。清单 6 显示在运行作业之后通过邮件发送给用户的输出。注意,这里的输出比对应的 cron 作业输出要简单一些。


清单 5. 使用 at 命令





[ian@lyrebird ~]$ at -f mycrontest.sh -v 10:25
Sat Jul 7 10:25:00 2007

job 5 at Sat Jul 7 10:25:00 2007



清单 6. 来自 at 的作业输出





From [email protected] Sat Jul 7 10:25:00 2007
Date: Sat, 7 Jul 2007 10:25:00 -0400
From: Ian Shields <[email protected]>
Subject: Output from your job 5
To: [email protected]

It is now 10:25:00 on Saturday



时间的设置可以非常复杂。清单 7 给出几个示例。参见 at 的手册页、/usr/share/doc/at/timespec 文件或 /usr/share/doc/at-3.1.10/timespec 这样的文件(这个示例中的 3.1.10 是 at 包的版本号)。


清单 7. at 命令使用的时间值





[ian@lyrebird ~]$ at -f mycrontest.sh 10pm tomorrow
job 14 at Sun Jul 8 22:00:00 2007
[ian@lyrebird ~]$ at -f mycrontest.sh 2:00 tuesday
job 15 at Tue Jul 10 02:00:00 2007
[ian@lyrebird ~]$ at -f mycrontest.sh 2:00 july 11
job 16 at Wed Jul 11 02:00:00 2007
[ian@lyrebird ~]$ at -f mycrontest.sh 2:00 next week
job 17 at Sat Jul 14 02:00:00 2007










nice 值

nice 值表示一个作业对于其他用户的优先程度。关于 nicerenice 命令的更多信息,参见教程 “LPI 101 考试准备:GNU 和 UNIX 命令”。


at 命令还有一个 -q 选项。随着队列的增长,作业的 nice 值也会增长。 还有一个 batch 命令,它与 at 命令相似,但是作业只在系统负载足够低时运行。这些特性的细节参见手册页。





















管理调度的作业


列出调度的作业


可以管理 cron 和 at 作业。使用 crontab 命令和 -l 选项列出 crontab,使用 atq 命令显示用 at 命令加入队列中的作业,见清单 8。


清单 8. 显示调度的作业





[ian@lyrebird ~]$ crontab -l
0,20,40 22-23 * 7 fri-sat /home/ian/mycrontest.sh
[ian@lyrebird ~]$ atq
16 Wed Jul 11 02:00:00 2007 a ian
17 Sat Jul 14 02:00:00 2007 a ian
14 Sun Jul 8 22:00:00 2007 a ian
15 Tue Jul 10 02:00:00 2007 a ian


如果希望查看 at 调度执行的实际命令,那么可以使用 at 命令并加上 -c 选项和作业号。您会注意到,在发出 at 命令时生效的大多数环境设置会随调度的作业一起保存。清单 9 给出清单 7 和清单 8 中作业 15 的部分输出。


清单 9. 使用 at -c 并加上作业号





#!/bin/sh
# atrun uid=500 gid=500
# mail ian 0
umask 2
HOSTNAME=lyrebird.raleigh.ibm.com; export HOSTNAME
SHELL=/bin/bash; export SHELL
HISTSIZE=1000; export HISTSIZE
SSH_CLIENT=9.67.219.151\ 3210\ 22; export SSH_CLIENT
SSH_TTY=/dev/pts/5; export SSH_TTY
USER=ian; export USER

HOME=/home/ian; export HOME
LOGNAME=ian; export LOGNAME

cd /home/ian || {
echo ‘Execution directory inaccessible’ >&2
exit 1
}
${SHELL:-/bin/sh} << `(dd if=/dev/urandom count=200 bs=1 \
2>/dev/null|LC_ALL=C tr -d -c ‘[:alnum:]’)`

#!/bin/bash
echo “It is now $(date +%T) on $(date +%A)”



注意,我们脚本文件的内容已经复制在一个 here-document 中,这个 here-document 将由 SHELL 变量指定的 shell 执行(如果没有设置 SHELL 变量,就使用 /bin/sh)。关于 here-document 的信息参见教程 “LPI 101 考试准备,主题 103:GNU 和 UNIX 命令”。


删除调度的作业


可以使用 cron 命令和 -r 选项删除所有调度的 cron 作业,见清单 10。


清单 10. 显示并删除 cron 作业





[ian@lyrebird ~]$ crontab -l
0,20,40 22-23 * 7 fri-sat /home/ian/mycrontest.sh
[ian@lyrebird ~]$ crontab -r
[ian@lyrebird ~]$ crontab -l
no crontab for ian


要删除系统 cron 或 anacron 作业,应该编辑 /etc/crontab、/etc/anacrontab 或者编辑或删除 /etc/cron.d 目录中的文件。


可以使用 atrm 命令加作业号删除用 at 命令调度的一个或多个作业。多个作业应该用空白分隔。清单 11 给出一个示例。


清单 11. 用 atq 和 atrm 显示并删除作业





[ian@lyrebird ~]$ atq
16 Wed Jul 11 02:00:00 2007 a ian
17 Sat Jul 14 02:00:00 2007 a ian
14 Sun Jul 8 22:00:00 2007 a ian
15 Tue Jul 10 02:00:00 2007 a ian
[ian@lyrebird ~]$ atrm 16 14 15
[ian@lyrebird ~]$ atq
17 Sat Jul 14 02:00:00 2007 a ian





















配置用户对作业调度的访问


如果文件 /etc/cron.allow 存在,那么非根用户必须在其中列出,才能使用 crontab 和 cron 设施。如果 /etc/cron.allow 不存在,但是 /etc/cron.deny 存在,那么其中列出的非根用户不能使用 crontab 或 cron 设施。如果这两个文件都不存在,那么只允许超级用户使用这个命令。空的 /etc/cron.deny 文件允许所有用户使用 cron 设施,这是默认情况。


/etc/at.allow 和 /etc/at.deny 文件对 at 设施起相似的作用。





















了解更多信息







如果想了解关于 Linux 管理任务的更多信息,请阅读教程 “LPI 102 考试准备:管理任务”,或者参见下面的 参考资料。不要忘记 rate 这个页面


参考资料

学习


获得产品和技术


  • 索取 SEK for Linux,这套 DVD(两张)包含来自 DB2®、Lotus®、Rational®、Tivoli® 和 WebSphere® 的最新 IBM 试用版 Linux 软件。


  • 使用 IBM 试用软件 构建您的下一个 Linux 开发项目,这些软件可以从 developerWorks 直接下载。


讨论




关于作者










Ian Shields


Ian Shields 为 developerWorks Linux 专区的许多 Linux 项目工作。他是 IBM 北卡罗莱那州 Research Triangle Park 的一名高级程序员。他于 1973 年作为一名系统工程师加入 IBM 位于澳大利亚堪培拉的子公司。之后,在加拿大蒙特利尔和北卡罗莱那州 RTP 从事通信系统和普及运算。他拥有多项专利并发表了若干篇论文。他毕业于 Australian National University,本科学位是纯数学和哲学。他拥有北卡罗来纳州立大学的计算机硕士和博士学位。您可以通过 [email protected] 与 Ian 联系。