Lesson 3: 駭客是怎麼做到的?
資料庫基礎與系統安全
script kiddie
以「駭客」自居並沾沾自喜的初學者。腳本小子不像真正的駭客那樣發現系統漏洞,他們通常使用別人開發的程式來惡意破壞他人系統。通常的刻板印象為一位沒有專科經驗的少年,破壞無辜網站企圖使得他的朋友感到驚訝。因而稱之為腳本小子。
來源:一樣是wikipedia
Distributed Denial of Service attack
簡單來說,你開一家餐廳,然後請了十個服務生
今天突然有一千個人湧進來,你的餐廳沒辦法再服務任何客人
你的餐廳就爆炸了
DDos就是有一堆「殭屍電腦」同時連進你的網站
因為流量太大所以負荷不住,網站就掛了
搶演唱會門票跟DDoS的原理差不多
記得上一堂講的DNS嗎?
也可以針對DNS做攻擊,不斷送出查詢
讓DNS Server一直處理不存在的網域
這樣子就無法回應新的需求,於是你就連不到網頁了
延伸閱讀:
http://d.gogo.la/thread-334629-1-1.html
被裝入木馬以後,你的電腦就開了一個後門
駭客可以從遠端連線到你的電腦,對你的電腦做任何事
可以利用你當跳板去入侵網站
可以讓你成為DDoS的其中一員
資料庫底下分成三個層級
第一層就像是excel檔案一樣,是最高的層級
第二層叫做Table,資料表,可以想成是excel的頁籤(tab)
第三層叫做column,欄位,就跟excel的欄位是一樣的
會員資料:帳號、密碼
會員訂單:訂單編號、會員帳號、訂購品項
遊戲資料:代碼、名稱、廠商、發行日期
儲值資料:代碼、儲值面額、名稱
發一個Request跟Server說:
我的帳號是huli,密碼是123,我要登入
$user = huli, $pwd=123
SELECT id FROM user where
username='$user' and password='$pwd'
SELECT id FROM user where
username='huli' and password='123'
這種查詢的語法,我們稱之為:SQL
全名叫做:Structured Query Language
這種加密是雙向的,加密以後可以被解密
例如說abcd加密成bcde,只是把每個字母向後移
解密的時候就往前移一個字即可
特色就是加密的流程只要倒著做就能解密
單向的加密,無法被解密
最為人知曉的演算法叫做md5
md5(1) = c4ca4238a0b923820dcc509a6f75849b
md5(11) = 6512bd43d9caa6e02c990b0a82652dca
輸入一樣,保證輸出一樣
但是沒辦法從輸出逆推回去輸入是什麼
所以一般來說,你的密碼存進資料庫以前
都會經過md5或是其他演算法產生一組字串
網站根本不知道你真正的密碼是多少
這也是為什麼你忘記密碼的時候,他只能幫你重設
而沒有辦法告訴你密碼是多少
如果某個網站可以告訴你你的密碼,這代表他用明碼存
那這個網站的安全性就十分令人擔心
延伸閱讀:密碼為什麼不能存「明文」?
前面說過,md5輸入一樣,輸出就會一樣
那我如果用程式去跑,把常見密碼的md5產生
比對一下我不就知道明碼是多少了?
例如說
md5(123456) = e10adc3949ba59abbe56e057f20f883e
這樣我只要看到後面那串字,我就知道明碼一定是123456
所以在實作上,比較安全的做法叫做「加鹽」
就是幫使用者產生一段亂數,配合著md5一起使用
例如說我產生一段:2fjfio33ojr3r3jo
而使用者的密碼是123456
存進資料庫時,存的資料就是md5(1234562fjfio33ojr3r3jo)
第一是長度變長,駭客很難知道明碼(除非他資料量夠大)
第二是就算知道了,也不能確定哪一段是明碼
$user = huli, $pwd=123
SELECT id FROM user where
username='$user' and password='$pwd'
SELECT id FROM user where
username='huli' and password='123'
SELECT id FROM user where
username='$user' and password='$pwd'
$user = ' or 1=1 --, $pwd=123
SELECT id FROM user where
username='' or 1=1 --' and password='123'
--是註解的意思,在這個符號之後的都會被忽略
一些設計不良的程式,會使得攻擊者可以執行特定程式碼
像是剛剛的例子,把原本看起來沒事的code
只要讓輸入變更一下,就變成意思完全不同的程式碼
解決方法是過濾傳進來的值,如果有特殊符號就處理掉
假設我們現在多了一個叫做name,姓名的欄位
只要帳號密碼符合,就會抓出name然後顯示出來
name = getName(username, password);
print(name);
name如果是huli,那就會顯示huli
所以會員登入以後,網站就是去資料庫抓出你的資料然後顯示
那如果你在註冊時填的姓名,是一段程式碼呢?
如果我的name是javascript:alert(1)
(這是一段程式碼,意思是跳出視窗並且顯示1)
server若是沒有做處理,直接輸出
就會讓使用者瀏覽這個網頁時,執行這段程式碼
攻擊者可以用這個漏洞做很多事
像是:偷cookie、改資料、把使用者轉址到其他網站
解決方法一樣是過濾特殊字元,讓它變成純文字顯示
不要讓任何人在你的網頁上執行程式碼
反之,只要你能找到可以執行程式碼的地方
就贏一半了