20年前偷懶修復的千年蟲bug歸來程序員:該來的總會來
新的十年開始了。二十年前,在千禧之年鐘聲敲響的時候,諸多Y2K應急隊的程序員坐在電腦前惴惴不安,他們此前剛剛用最簡單易行的“懶人方法”修補了一個被稱為“千年蟲”(Millennium Bug,又稱Y2000 problem,簡稱“Y2K”)的大bug。二十年後,這群程序員老了,但是新一代的青年程序員又要為老一輩的懶惰而付出代價。
據《紐約時報》報導,紐約的停車收費表從2020年1月1日開始不支持信用卡付款,整個城市的一萬多個計費表已手動更新,僅通過現金或ParkNYC接受付款;波蘭公司Novitus生產的收銀機由於記錄時間故障而無法打印收據;視頻遊戲WWE 2K20於2020年1月1日午夜停止工作;華為手錶和部分設備丟掉了新年伊始兩三天的TrueSleep睡眠數據,需要更新並重啟… …
紐約市交通局表示,停車計時器的信用卡支付軟件設定在1 月1 日失效,導致了一起大規模故障(來源:The New York Times)
程序員Jef Poskanzer在推特上發文:似乎有相當數量的系統出現#2020錯誤。當年解決Y2K問題的方案把這個問題推遲了20年……20年後的今天,當時的一些系統仍然還在使用,系統以為我們在1920年。”
Jef Poskanzer 的推文(來源:Twitter 截圖)
千禧年前後出生的青少年們或許很少有人知道“千年蟲”。
大約在20世紀80年代中期以前投用的系統上,囿於存儲空間有限,再加上人們普遍覺得系統更新會很快,所以程序員大多采用兩位數來表示年份,比如06/15/98 ,而不是06/15/1998。但是到了2000年,系統只知道是01/01/00,不知道這是1900還是2000。
千年蟲主要集中在配備較早的主機系統上,如在IBM 4381,IBM AS/400等機型上運行的應用程序,比如美國的AT&T電訊公司,其內部就有超過3.6億行的應用程序需要檢測是否存在Y2K問題。另外,在自動化儀器儀表、電梯、警報系統、恆溫燈等嵌入式設備也容易存在千年蟲隱患。
視頻Y2K 啟示錄(來源:YouTube)
計算機在上世紀六七十年代開始普及,到九十年代,人們開始意識到問題的嚴重性:不知道從1999年最後一天的23:59到2000年第一天的00:00的轉變意味著什麼?在渲染和炒作下,大眾的驚恐程度不亞於“2012”。人們猜測,如果程序停止運行、崩潰或者發出錯誤指令,是否影響到銀行、電站、航線等等,存款會一夜清零、恐怖襲擊、飛機墜落、股市崩潰,世界陷入混亂?
當時甚至有媒體報導,有人把山洞當做避難所,存儲了很多食物、醫療包等必需品,還有一些人把銀行存款紛紛取出來或者是購買黃金。
1999 年1 月18 日,TIME 的封面(來源:Time)
為了避免“災難”發生,政府和企業動用大量資源查找和修復這個bug。有報導顯示,當時克林頓政府和業內人士估計,用“windowing”的方式修補80%的計算機,預計耗資數千億美元。BBC報導認為全球花在防備千年蟲上的費用在3000億到5000億美元之間。真實耗資目前無法考證。也有言論說千年蟲是個商業大騙局。
當時修復bug的方式有兩種:完全重寫代碼,或者採用“windowing”的方式快速修復。“windowing”就是把00到20之間的所有日期都當做20XX年而不是19XX年。很顯然,相比於把所有兩位數表示的年份都修改成四位數,後一種方式更省錢、更快而且更容易。
從1970/01/01 開始,很多編程語言和系統都把日期時間以秒來處理,也叫Unix time。因此,鑑於中點1970 的重要性,編碼人員選擇1920 到2020 作為標準窗口。
Unix time被廣泛用於各種行業操作系統,並被視為是一種標準。Unix和Windows系統有環境變量來為系統設置“轉折年”。“轉折年”以後的任何一年屬於本世紀,“轉折年”以及“轉折年”之前的任意一年屬於上個世紀。但是一些產品,如Microsoft Excel 95使用的是1920-2020年的windowing,在解決千年蟲問題之後,僅僅過20年就有可能再次出現日期錯誤。
2020 年“Y2K” 又回來了(來源:Popular Mechanics)
當時的專家認為,等到程序員投入大量的資金和時間去永久修復好這些bug 之後,系統早就被更換了。所以,儘管“windowing” 修復的程序智能使用二三十年,專家也覺得足夠了。
倫敦經濟學院(London School of Economics) 的迪倫· 穆爾文(Dylan Mulvin) 表示:“windowing 是所有解決方案中最糟糕的一種,即便是在千年蟲問題期間。”
2020年的到來,意味著我們已經進入到了1920-2020窗口期的末端。2019年11月,由於被發現容易受到Y2020“攻擊”,大數據公司Splunk向用戶推出了修復服務,它的用戶涵蓋了美國《財富》一百強公司中的92家。由於各家公司尚未披露相關細節,目前還不清楚“Y2020”將持續多久。
另外,在2038年我們將面臨另一個數據存儲問題。32位的Unix和Linux,能存儲的最大數字為2的31次方,即2147483647。從1997年開始計算,2147483647用來表示的秒數最多只能用到2038年01月19日03時14分07秒,在這個時間之後,系統會回到- 2147483648,代表的時期是1901年12月13日20時45分52秒。
不同於千年蟲,2038 會影響的不僅僅是應用層,而是會影響到最底層的時間控制功能。不過幸運的是,如果能在2038 年之前把所有32 位系統淘汰並採用64 位的話,我們將會巧妙地躲開2038 問題。