本節包括原始程式碼之外的所有內容,但對於建立中產品的安全性仍至關重要。由於此領域所涵蓋的問題與原始程式碼沒有直接關係,因此我們將其與其他領域分開。
https_redirect
設為 false
來定義 URL 對應,以允許用戶端使用 HTTP 進行通訊。
resource "google_compute_url_map" "urlmap" {
...
default_url_redirect {
...
https_redirect = false
...
}
...
}
rsasha1
啟用 DNSSEC 的 Terraform 組態。
resource "google_dns_managed_zone" "zone-demo" {
...
dnssec_config {
default_key_specs {
algorithm = "rsasha1"
...
}
}
...
}
networking_mode
設定為 ROUTES
而不啟用 VPC 原生叢集。
resource "google_container_cluster" "cluster_demo" {
...
networking_mode = "ROUTES"
..
}
X-XSS-Protection
設定為 1; mode=block
,會在舊版瀏覽器中開啟 Cross-site scripting 弱點。X-XSS-Protection
是由 Microsoft 引入的 HTTP 標頭,後來由其他瀏覽器所採用。這旨在協助阻止 Cross-Site Scripting
攻擊成功,但不慎導致弱點的情況,使得安全網站易受攻擊[1]。因此,不應在舊版 Internet Explorer 中使用此標頭,並且應透過將標頭設定為 0
將其停用。Express
應用程式中的 Helmet
中介軟體,以針對所有版本的 Internet Explorer 啟用此標頭:
var express = require('express');
var app = express();
var helmet = require('helmet');
...
app.use(helmet.xssFilter({ setOnOldIE: true}));
...
Application_BeginRequest
為空,或不包括將 X-Content-Type-Options
設定為 nosniff
的函數呼叫,或嘗試移除該表頭。X-Content-Type-Options: nosniff
。X-Content-Type-Options
設定為 nosniff
。X-Content-Type-Options: nosniff
用於可能含有使用者可控制內容的每個頁面中。net.http.DetectContentType()
確定資源 Content-Type:
...
resp, err := http.Get("http://example.com/")
if err != nil {
// handle error
}
defer resp.Body.Close()
body, err := ioutil.ReadAll(resp.Body)
content_type := DetectContentType(body)
...
X-Content-Type-Options
設定為 nosniff
,或明確停用此安全性標頭。X-Content-Type-Options: nosniff
。
<http auto-config="true">
...
<headers>
...
<content-type-options disabled="true"/>
</headers>
</http>
X-Content-Type-Options
設定為 nosniff
,或明確停用此安全性標頭。X-Content-Type-Options: nosniff
。X-Content-Type-Options
設為 nosniff
,或明確停用此安全性表頭。X-Content-Type-Options: nosniff
。memset()
來清除記憶體中的密碼。
void GetData(char *MFAddr) {
char pwd[64];
if (GetPasswordFromUser(pwd, sizeof(pwd))) {
if (ConnectToMainframe(MFAddr, pwd)) {
// Interaction with mainframe
}
}
memset(pwd, 0, sizeof(pwd));
}
memset()
的呼叫會被當作一個無效儲存清除,因為 pwd
的緩衝區在它的數值被覆蓋之後不會再次被使用 [2]。因為緩衝區 pwd
包含一個敏感值,所以如果資料經常被留在記憶體中,應用程式就會容易受到攻擊。如果攻擊者能夠存取記憶體正確的區域,他們就能使用復原後的密碼來取得對系統的控制。memset()
的呼叫被寫入記憶體之後不會被使用,所以編譯器將這個呼叫解譯為一段 Dead Code;而這樣做實際上很顯然會引起一個安全問題。這裏的問題是,許多編譯器和許多程式語言並沒有在其提高效率時考慮到此問題和其他安全問題。
char *buf;
int len;
...
len = 1<<30;
if (buf+len < buf) //wrap check
[handle overflow]
buf + len
大於 2^32
,因此產生的值小於 buf
。但是,由於指標的算數運算溢位是未定義的行為,因此某些編譯器會假設 buf + len >= buf
,並最佳化封裝檢查。此最佳化操作的結果是,此區塊後的程式碼很容易出現 Buffer overflow。static files
應用程式的 serve
視圖,此視圖並非專用於在生產環境中部署。根據 Django 說明文件:static files
工具主要用於協助取得已在生產中成功部署的靜態檔案。這通常是指單獨、專用的靜態檔案伺服器,於本機開發時,此伺服器的運作成本極高。因此,靜態檔案應用程式隨附臨時應急的協助程式視圖,用來在開發期間於本機執行檔案。DEBUG
為 True
時,此視圖才有效。admin
應用程式部署在可預測的 URL 中:
from django.conf.urls import patterns
from django.contrib import admin
admin.autodiscover()
urlpatterns = patterns('',
...
url(r'^admin/', include(admin.site.urls)),
...
<Realm className="org.apache.catalina.realm.JAASRealm"
appName="SRN"
userClassNames="com.srn.security.UserPrincipal"
roleClassNames="com.srn.security.RolePrincipal"/>
Realm
標籤有一個名為 debug
的選擇性屬性,由它來指示記錄層級。數字越大,記錄的訊息就越詳細。如果除錯層級設定過高,Tomcat 會把所有的使用者名稱和密碼以純文字方式寫入至記錄檔中。Tomcat JAASRealm
相關的除錯訊息的臨界值是 3 (3 或更高表示有問題,2 或更低表示正常),但此臨界值可能會因 Tomcat 提供不同的 realm 類型而有所不同。http://host/page.jsp%00
或 http://host/page.js%2570
等精心設計的要求。更糟的是,如果應用程式允許使用者上傳任意檔案,攻擊者可能使用此機制,上傳以 JSP 型式製作的惡意程式碼,並要求已上傳頁面,以在伺服器上執行惡意程式碼。
<security-constraint>
<web-resource-collection>
<web-resource-name>JSP Access for Everyone!</web-resource-name>
<description>Allow any user/role access to JSP</description>
<url-pattern>*.jsp</url-pattern>
</web-resource-collection>
<auth-constraint>
<role-name>*</role-name>
</auth-constraint>
</security-constraint>
web.xml
檔案中的項目定義了兩個 admin
角色。
<security-constraint>
<web-resource-collection>
<web-resource-name>AdminPage</web-resource-name>
<description>Admin only pages</description>
<url-pattern>/auth/noaccess/*</url-pattern>
</web-resource-collection>
<auth-constraint>
<description>Administrators only</description>
<role-name>admin</role-name>
</auth-constraint>
</security-constraint>
...
<security-role>
<description>Administrator</description>
<role-name>admin</role-name>
</security-role>
<security-role>
<description>Non-Administrator</description>
<role-name>admin</role-name>
</security-role>
/servletA/*
。
<servlet-mapping>
<servlet-name>ServletA</servlet-name>
<url-pattern>/servletA/*</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>ServletB</servlet-name>
<url-pattern>/servletA/*</url-pattern>
</servlet-mapping>