錯誤 #5
public class Barrel {
// By default, a barrel contains one rhesus monkey.
private static Monkey[] defaultMonkeys =
new[] { new RhesusMonkey() };
// backing store for property.
private IEnumerable<Monkey> monkeys = null;
public IEnumerable<Monkey> Monkeys {
get {
if (monkeys == null) {
if (MonkeysReady())
monkeys = PopulateMonkeys();
else
monkeys = defaultMonkeys;
}
return monkeys;
}
}
}
答案:這是一個難題。此類作者認為它們是安全高效的。其後備存儲是保密的,屬性為只讀,屬性類型為 IEnumerable<T>,因此調用方無法執行任何操作,只能讀取 Barrel 的狀態。
作者忘記了心懷叵測的調用方可能會嘗試將屬性的返回值轉換為 Monkey[]。如果有兩個 Barrel,每個都有默認的 Monkey 列表,那麼擁有其中一個 Barrel 的惡意調用方則可以使用其他任何 Monkey(或 null)來替換靜態默認列表中的 RhesusMonkey,從而實際改變另一個 Barrel 的狀態。
此處的解決方案是緩存 ReadOnlyCollection<T> 或其他某個真正的只讀存儲,以保護底層數組免受調用方惡意或意外的轉換。如果您抓住了這一點,就給自己加兩分。
錯誤 #6 (C#)
protected void Page_Load(object sender, EventArgs e) {
string lastLogin = Request["LastLogin"];
if (String.IsNullOrEmpty(lastLogin)) {
HttpCookie lastLoginCookie = new HttpCookIE("LastLogin",
DateTime.Now.ToShortDateString());
lastLoginCookIE.Expires = DateTime.Now.AddYears(1);
Response.Cookies.Add(lastLoginCookIE);
}
else {
Response.Write("Welcome back! You last logged in on " + lastLogin);
Response.CookIEs["LastLogin"].Value =
DateTime.Now.ToShortDateString();
}
}
答案:這是一個非常簡單的、跨站點的腳本編寫漏洞,也是 Web 上最常見的漏洞。盡管代碼似乎暗示 lastLogin 值始終來自 cookie,但實際上 HttpRequest.Item 屬性更傾向於使用來自查詢字符串的值,而不是來自 cookIE 的值。
換句話說,無論 lastLogin cookIE 被設置為何值,只要攻擊者將成對的名稱/值 lastLogin=<script>alert('0wned!')</script> 添加到查詢字符串中,應用程序就會為 lastLogin 變量的值選擇惡意腳本輸入。如果您的回答是 XSS,則給自己加一分。
錯誤 #7 (C#)
private decimal? lookupPrice(XMLDocument doc) {
XMLNode node = doc.SelectSingleNode(
@"//products/product[id/text()='" +
Request["itemId"] + "']/price");
if (node == null)
return null;
else
return (Convert.ToDecimal(node.InnerText));
}
答案:如果您說是 XPath 注入,則給自己加一分。XPath 注入的工作原理與其同類但卻更為著名(也可以說是臭名昭著)的 SQL 注入完全一樣。此代碼創建了一個將 XPath 代碼和未經驗證的保留用戶輸入合並在一起的查詢,因此很容易受到注入攻擊。任何應用程序如果它所處理的文本隨後將被用於執行某種形式的操作,則它們都面臨注入攻擊的威脅。