class AccessLevel{
public static final int ROOT = 0;
//...
public static final int NONE = 9;
}
//...
class User {
private static int access;
public User(){
access = AccessLevel.ROOT;
}
public static int getAccessLevel(){
return access;
}
//...
}
class RegularUser extends User {
private static int access;
public RegularUser(){
access = AccessLevel.NONE;
}
public static int getAccessLevel(){
return access;
}
public static void escalatePrivilege(){
access = AccessLevel.ROOT;
}
//...
}
//...
class SecureArea {
//...
public static void doRestrictedOperation(User user){
if (user instanceof RegularUser){
if (user.getAccessLevel() == AccessLevel.ROOT){
System.out.println("doing a privileged operation");
}else{
throw new RuntimeException();
}
}
}
}
getAccessLevel()
をインスタンス user
にコールしているのであって、クラス User
や RegularUser
にコールしているのではないため、この場合は常に true
が返され、instanceof
が使用される場合でも、if/else
ブロックのこの部分に到達するために操作が制限されます。
private void writeObject(java.io.ObjectOutputStream out) throws IOException;
private void readObject(java.io.ObjectInputStream in) throws IOException, ClassNotFoundException;
private void readObjectNoData() throws ObjectStreamException;
serialPersistentFields
を正しく使用するには、private
、static
、および final
として宣言する必要があります。serialPersistentFields
配列内で指定して、クラスの Serializable フィールドを手動で定義できるようになります。この機能は、serialPersistentFields
が private
、static
、および final
として宣言されている場合にのみ奏功します。serialPersistentFields
が、private
、static
、および final
ではないため、Serializable
フィールドの定義には使用されません。
class List implements Serializable {
public ObjectStreamField[] serialPersistentFields = { new ObjectStreamField("myField", List.class) };
...
}
java.util.Arrays.equals().
ではなく Object.equals()
をコールしています。 Object.equals()
をコールすることは、多くの場合誤りです。この関数は配列の要素ではなく配列のアドレスが等価かどうかをチェックするため、通常は java.util.Arrays.equals()
で置き換える必要があります。 Object.equals()
関数を使ってチェックしようとしています。
...
int[] arr1 = new int[10];
int[] arr2 = new int[10];
...
if (arr1.equals(arr2)){
//treat arrays as if identical elements
}
...
System.Object.Equals()
を上書きするためのものです。
public boolean Equals(string obj) {
...
}
System.Object.Equals()
は、object
タイプの引数を取るため、メソッドがコールされることはありません。Object.equals()
を上書きするためのものです。
public boolean equals(Object obj1, Object obj2) {
...
}
Object.equals()
は単一引数のみを受け取るため、Example 1
のメソッドがコールされることはありません。getOutputStream
をコールした後に、getWriter()
をコールする場合もエラーが発生しやすくなります。HttpServletRequest
の転送、HttpServletResponse
のリダイレクト、またはサーブレットの出力ストリームバッファーのフラッシュによって、関連ストリームがコミットされます。後続のバッファーがストリームをリセットまたはコミットすると (追加のフラッシュまたはリダイレクトなど)、IllegalStateException
となります。ServletOutputStream
または PrintWriter
のいずれか (両方ではありません) を使用して、レスポンスストリームへのデータの書き込みが許可されます。getOutputStream()
をコールした後に、getWriter()
をコールする、また逆の処理を行った場合、IllegalStateException
となります。IllegalStateException
によって、レスポンスハンドラの実行が防止され、レスポンスがドロップすることになります。これによりサーバーの動作が不安定になります。また、サーブレットが適切に実装されていないことを示します。例 2: 逆に、次のコードは、リクエストが転送された後に、書き込みを行い、
public class RedirectServlet extends HttpServlet {
public void doGet(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException {
...
OutputStream out = res.getOutputStream();
...
// flushes, and thereby commits, the output stream
out.flush();
out.close(); // redirecting the response causes an IllegalStateException
res.sendRedirect("http://www.acme.com");
}
}
PrintWriter
のバッファーをフラッシュしようとしています。
public class FlushServlet extends HttpServlet {
public void doGet(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException {
...
// forwards the request, implicitly committing the stream
getServletConfig().getServletContext().getRequestDispatcher("/jsp/boom.jsp").forward(req, res);
...
// IllegalStateException; cannot redirect after forwarding
res.sendRedirect("http://www.acme.com/jsp/boomboom.jsp");
PrintWriter out = res.getWriter();
// writing to an already-committed stream will not cause an exception,
// but will not apply these changes to the final output, either
out.print("Writing here does nothing");
// IllegalStateException; cannot flush a response's buffer after forwarding the request
out.flush();
out.close();
}
}
Content-Length
ヘッダーには負の数が設定されています。Content-Length
ヘッダーを設定した開発者は、0
または正の数をContent-Length
を設定することになります。
URL url = new URL("http://www.example.com");
HttpURLConnection huc = (HttpURLConnection)url.openConnection();
huc.setRequestProperty("Content-Length", "-1000");
Content-Length
ヘッダーには負の数が設定されています。Content-Length
ヘッダーを設定した開発者は、0
または正の数をContent-Length
ヘッダーに誤って負の数を設定しています。
xhr.setRequestHeader("Content-Length", "-1000");
java.io.Serializable
を実装している内部クラスは、問題が発生したり、外部クラスから情報が漏えいする可能性があります。
...
class User implements Serializable {
private int accessLevel;
class Registrator implements Serializable {
...
}
}
Example 1
では、内部クラス Registrator
がシリアライズされると、外部クラス User
からのフィールド accessLevel
もシリアライズされます。synchronized
を宣言した親クラスは、複数のスレッドが同じインスタンスにアクセスするときに、正しい動作を保証します。すべての上書きメソッドを、synchronized
として宣言する必要があります。そうしないと、予期せぬ動作が発生する可能性があります。Foo
がクラス Bar
を上書きしていますが、メソッド synchronizedMethod
を synchronized
に宣言していません。
public class Bar {
public synchronized void synchronizedMethod() {
for (int i=0; i<10; i++) System.out.print(i);
System.out.println();
}
}
public class Foo extends Bar {
public void synchronizedMethod() {
for (int i=0; i<10; i++) System.out.print(i);
System.out.println();
}
}
Foo
のインスタンスが、タイプ Bar
にキャストされる可能性があります。同じインスタンスが 2 つのスレッドに指定されており、synchronizedMethod
が繰り返し実行される場合、動作が予期できなくなります。obj.Equals(null)
は常に false となります。Equals()
メソッドを使用してオブジェクトを null
と比較します。Equals()
メソッドのコントラクトでは、この比較で常に false が戻される必要があります。obj.equals(null)
は常に false となります。equals()
メソッドを使用してオブジェクトを null
と比較します。オブジェクトが null
ではないため、この比較は常に false を返します。(オブジェクトが null
の場合、プログラムは NullPointerException
を発生させます)。readObject()
メソッドは、オーバーライドされる可能性のある関数を呼び出します。readObject()
は、コンストラクターのように振る舞うため、オブジェクトの初期化は関数が終わるまで完了しません。そのため、Serializable
の readObject()
関数がオーバーライド関数をコールすると、完全に初期化される前にオブジェクトの状態にオーバーライド メソッドがアクセスできるようになります。readObject()
関数は、オーバーライドされる可能性のあるメソッドをコールしています。
...
private void readObject(final ObjectInputStream ois) throws IOException, ClassNotFoundException {
checkStream(ois);
ois.defaultReadObject();
}
public void checkStream(ObjectInputStream stream){
...
}
checkStream()
と括弧で囲まれたクラスは final
ではなくパブリックであるため、関数がオーバーライドできるようになります。つまり、攻撃者は checkStream()
関数をオーバーライドし、デシリアライゼーションの間、オブジェクトにアクセスできるようになります。
Marker child = MarkerManager.getMarker("child");
Marker parent = MarkerManager.getMarker("parent");
child.addParents(parent);
parent.addParents(child);
String toInfinity = child.toString();
toString()
を子が呼び出すと、スタック オーバーフロー例外 (スタック枯渇) がトリガーされます。この例外は、子と親の間の循環リンクが原因で発生します。String
オブジェクトの比較は、信頼できないため、実行しないでください。String
オブジェクトと比較するには、まず String
オブジェクトに変換します。通常、Double.toString()
のような関数を使います。浮動小数点の変数のタイプと値により、String
オブジェクトに変換すると、結果は "NaN"、"Infinity"、"-Infinity"、ゼロを含む一定の小数値を持つ値、または指数フィールドを含む値になる場合があります。16 進数の String に変換された場合も、表現が大幅に異なることがあります。String
と比較しています。
...
int initialNum = 1;
...
String resultString = Double.valueOf(initialNum/10000.0).toString();
if (s.equals("0.0001")){
//do something
...
}
...
ToString()
は配列でコールされます。ToString()
がコールされているということは、開発者が配列の内容を文字列として返そうとしていることを意味します。しかし、配列で ToString()
を直接コールすると、その配列のタイプを含んだ文字列値が返されます。System.String[]
を出力します。
String[] stringArray = { "element 1", "element 2", "element 3", "element 4" };
System.Diagnostics.Debug.WriteLine(stringArray.ToString());
toString()
は配列でコールされます。toString()
がコールされているということは、開発者が配列の内容を文字列として返そうとしていることを意味します。しかし、配列で toString()
を直接コールすると、その配列のタイプおよびメモリのハッシュコードを含んだ文字列値が返されます。[Ljava.lang.String;@1232121
を出力します。
String[] strList = new String[5];
...
System.out.println(strList);
APPHOME
を使用してインストール先ディレクトリが決定され、指定されたディレクトリからの相対パスに基づいて初期化スクリプトが実行されます。
...
CALL FUNCTION 'REGISTRY_GET'
EXPORTING
KEY = 'APPHOME'
IMPORTING
VALUE = home.
CONCATENATE home INITCMD INTO cmd.
CALL 'SYSTEM' ID 'COMMAND' FIELD cmd ID 'TAB' FIELD TABL[].
...
Example 1
のコードでは、悪意ある INITCMD
を含んだ別のパスを参照するようにレジストリエントリ APPHOME
を変更することにより、攻撃者はアプリケーションの任意のコマンドを高い権限で実行できます。このプログラムはレジストリから読み取った値の検証を行わないので、レジストリキー APPHOME
の値を制御できれば、攻撃者はアプリケーションを操作して悪意のあるコードを実行させ、システムを支配下に置くことができます。rman
ユーティリティに対するバッチファイルラッパーを使用して Oracle データベースのバックアップを開始し、その後 cleanup.bat
スクリプトを実行して一部のテンポラリ ファイルを削除できるインターフェイスを持つ Web アプリケーションのものです。スクリプト rmanDB.bat
は、実行するバックアップのタイプを指定するコマンドライン パラメーターを 1 つ受け取ります。データベースへのアクセスが制限されているため、アプリケーションは権限を持つユーザーとしてバックアップを実行します。
...
btype = request->get_form_field( 'backuptype' )
CONCATENATE `/K 'c:\\util\\rmanDB.bat ` btype `&&c:\\util\\cleanup.bat'` INTO cmd.
CALL FUNCTION 'SXPG_COMMAND_EXECUTE_LONG'
EXPORTING
commandname = cmd_exe
long_params = cmd_string
EXCEPTIONS
no_permission = 1
command_not_found = 2
parameters_too_long = 3
security_risk = 4
OTHERS = 5.
...
backuptype
パラメーターを検証しないことです。通常、関数モジュール SXPG_COMMAND_EXECUTE_LONG
は複数のコマンドを実行しませんが、この例のプログラムは最初に cmd.exe
シェルを実行して、CALL 'SYSTEM'
を 1 回コールするだけで複数のコマンドを実行しています。呼び出されたシェルは、2 つのアンパサンドで区切られた複数のコマンドを実行できます。攻撃者が "&& del c:\\dbms\\*.*"
という形式の文字列を渡すと、アプリケーションは、プログラムにより指定された他のコマンドとともにこのコマンドを実行します。アプリケーションはその性質上、データベースとのやり取りに必要な権限で実行されています。このため、攻撃者が挿入したコマンドも、その権限で実行されます。/var/yp
ディレクトリでの make
コマンドの実行が含まれます。
...
MOVE 'make' to cmd.
CALL 'SYSTEM' ID 'COMMAND' FIELD cmd ID 'TAB' FIELD TABL[].
...
CALL 'SYSTEM'
のコールを実行する前に環境をクリーンにできていないことです。攻撃者が $PATH
変数を変更して、make
という名前の悪意あるバイナリを参照させ、攻撃者の環境でプログラムが実行されるようにすると、本来のバイナリでなく悪意あるバイナリがロードされます。アプリケーションの性質上、このバイナリはシステム操作の実行に必要な権限で実行されます。つまり、攻撃者の make
もその権限で実行されるため、攻撃者がシステムを完全に制御してしまう可能性があります。
...
var fs:FileStream = new FileStream();
fs.open(new File(String(configStream.readObject())+".txt"), FileMode.READ);
home = String(fs.readObject(home));
var cmd:String = home + INITCMD;
fscommand("exec", cmd);
...
Example 1
のコードでは、悪意ある INITCMD
を含んだ別のパスを参照するように設定ファイル configStream
の内容を変更することにより、攻撃者はアプリケーションの任意のコマンドを高い権限で実行できます。このプログラムではファイルから読み取った値の検証が実行されないため、攻撃者がこの値を制御できる場合、アプリケーションを操って悪意のあるコードを実行し、システムを制御できます。rman
ユーティリティに対するバッチファイルラッパーを使用して Oracle データベースのバックアップを開始し、その後 cleanup.bat
スクリプトを実行して一部のテンポラリ ファイルを削除できるインターフェイスを持つ Web アプリケーションのものです。スクリプト rmanDB.bat
は、実行するバックアップのタイプを指定するコマンドライン パラメーターを 1 つ受け取ります。データベースへのアクセスが制限されているため、アプリケーションは権限を持つユーザーとしてバックアップを実行します。
...
var params:Object = LoaderInfo(this.root.loaderInfo).parameters;
var btype:String = String(params["backuptype"]);
var cmd:String = "cmd.exe /K \"c:\\util\\rmanDB.bat " + btype + "&&c:\\util\\cleanup.bat\"";
fscommand("exec", cmd);
...
backuptype
パラメーターを検証しないことです。通常、関数 fscommand()
は複数のコマンドを実行しませんが、この例のプログラムは最初に cmd.exe
シェルを実行して、fscommnd()
を 1 回コールするだけで複数のコマンドを実行しています。呼び出されたシェルは、2 つのアンパサンドで区切られた複数のコマンドを実行できます。攻撃者が "&& del c:\\dbms\\*.*"
という形式の文字列を渡すと、アプリケーションは、プログラムにより指定された他のコマンドとともにこのコマンドを実行します。アプリケーションはその性質上、データベースとのやり取りに必要な権限で実行されています。このため、攻撃者が挿入したコマンドも、その権限で実行されます。/var/yp
ディレクトリでの make
コマンドの実行が含まれます。
...
fscommand("exec", "make");
...
fscommand()
のコールを実行する前に環境をクリーンにできていないことです。攻撃者が $PATH
変数を変更して、make
という名前の悪意あるバイナリを参照させ、攻撃者の環境でプログラムが実行されるようにすると、本来のバイナリでなく悪意あるバイナリがロードされます。アプリケーションの性質上、このバイナリはシステム操作の実行に必要な権限で実行されます。つまり、攻撃者の make
もその権限で実行されるため、攻撃者がシステムを完全に制御してしまう可能性があります。APPHOME
を使用してインストール先ディレクトリが決定され、指定されたディレクトリからの相対パスに基づいて初期化スクリプトが実行されます。
...
string val = Environment.GetEnvironmentVariable("APPHOME");
string cmd = val + INITCMD;
ProcessStartInfo startInfo = new ProcessStartInfo(cmd);
Process.Start(startInfo);
...
Example 1
のコードでは、悪意ある INITCMD
を含んだ別のパスを参照するようにシステムプロパティ APPHOME
を変更することにより、攻撃者はアプリケーションの任意のコマンドを昇格した権限で実行できます。このプログラムは環境から読み取った値の検証を行わないので、システムプロパティ APPHOME
の値を制御できれば、攻撃者はアプリケーションを操作して悪意のあるコードを実行させ、システムを支配下に置くことができます。rman
ユーティリティに対するバッチファイルラッパーを使用して Oracle データベースのバックアップを開始し、その後 cleanup.bat
スクリプトを実行して一部のテンポラリ ファイルを削除できるインターフェイスを持つ Web アプリケーションのものです。スクリプト rmanDB.bat
は、実行するバックアップのタイプを指定するコマンドライン パラメーターを 1 つ受け取ります。データベースへのアクセスが制限されているため、アプリケーションは権限を持つユーザーとしてバックアップを実行します。
...
string btype = BackupTypeField.Text;
string cmd = "cmd.exe /K \"c:\\util\\rmanDB.bat"
+ btype + "&&c:\\util\\cleanup.bat\""));
Process.Start(cmd);
...
BackupTypeField
をいっさい検証しないことです。通常、Process.Start()
関数は複数のコマンドを実行しませんが、この例のプログラムは最初に cmd.exe
シェルを実行して、Process.Start()
を 1 回コールするだけで複数のコマンドを実行しています。呼び出されたシェルは、2 つのアンパサンドで区切られた複数のコマンドを実行できます。攻撃者が "&& del c:\\dbms\\*.*"
という形式の文字列を渡すと、アプリケーションは、プログラムにより指定された他のコマンドとともにこのコマンドを実行します。アプリケーションはその性質上、データベースとのやり取りに必要な権限で実行されています。このため、攻撃者が挿入したコマンドも、その権限で実行されます。update.exe
コマンドの実行が含まれます。
...
Process.Start("update.exe");
...
Process.start()
のコールを実行する前に環境をクリーンにできていないことです。攻撃者が $PATH
変数を変更して、update.exe
という名前の悪意あるバイナリを参照させ、攻撃者の環境でプログラムが実行されるようにすると、本来のバイナリでなく悪意あるバイナリがロードされます。アプリケーションの性質上、このバイナリはシステム操作の実行に必要な権限で実行されます。つまり、攻撃者の update.exe
もその権限で実行されるため、攻撃者がシステムを完全に制御してしまう可能性があります。setuid root
にインストールされている、システム管理者用の学習ツールです。権限が設定されているシステム ファイルを変更したりシステムに損傷を与えたりすることができない状態で、それらのファイルをチェックすることができます。
int main(char* argc, char** argv) {
char cmd[CMD_MAX] = "/usr/bin/cat ";
strcat(cmd, argv[1]);
system(cmd);
}
root
権限で実行されるため、system()
のコールも root
権限で実行されます。ユーザーが標準的なファイル名を指定した場合、コールは想定どおりに動作します。しかし、攻撃者が ";rm -rf /"
という形の文字列を渡すと、system()
へのコールでは引数がないため cat
を実行できず、root パーティションの内容を回帰的に削除してしまいます。$APPHOME
を使用してアプリケーションのインストール先ディレクトリを判断し、そのディレクトリの初期化スクリプトを実行します。
...
char* home=getenv("APPHOME");
char* cmd=(char*)malloc(strlen(home)+strlen(INITCMD));
if (cmd) {
strcpy(cmd,home);
strcat(cmd,INITCMD);
execl(cmd, NULL);
}
...
Example 1
に例示するコードを利用すれば、攻撃者はアプリケーションの権限を高めて任意のコマンドを実行できます。この例では、攻撃者は環境変数 $APPHOME
を変更して、INITCMD
の悪意ある改変版が置かれた別のパスを指定することができます。プログラムでは環境から読み取った値を検証しないため、攻撃者は環境変数を制御することでアプリケーションを操って悪意あるコードを実行させることができます。/var/yp
ディレクトリでの make
の実行も含まれます。プログラムはパスワードレコードも更新するので setuid root
にインストールされている、ということに注意してください。make
を呼び出します。
system("cd /var/yp && make &> /dev/null");
system()
に渡される引数を制御できません。ただし、プログラムでは make
の絶対パスが指定されておらず、コマンドを呼び出す前にすべての環境変数がチェックされません。このため、攻撃者は $PATH
変数を変更して、make
という名前の悪意あるバイナリを参照させ、シェル プロンプトから CGI スクリプトを実行させることができます。また、プログラムが setuid root
にインストールされているため、攻撃者の make
は root
権限で実行されます。CreateProcess()
を直接または _spawn()
ファミリの関数のいずれかへのコールを介して呼び出す場合、実行可能ファイルまたはパスにスペースがあるときは注意が必要です。
...
LPTSTR cmdLine = _tcsdup(TEXT("C:\\Program Files\\MyApplication -L -S"));
CreateProcess(NULL, cmdLine, ...);
...
CreateProcess()
がスペースを解析する方法では、オペレーティングシステムが最初に実行を試みる実行可能ファイルは、MyApplication.exe
ではなく Program.exe
です。このため、攻撃者がシステムに Program.exe
という名前の悪意あるアプリケーションをインストールできる場合、Program Files
ディレクトリを使用して CreateProcess()
を不正にコールするプログラムは、目的のアプリケーションの代わりにこのアプリケーションを実行します。system()
、exec()
、および CreateProcess()
といった関数は、自身をコールするプログラムの環境を使用するため、攻撃者はそれらのコールの動作を変更できる可能性があります。$PATH
やその他の要素を変えることで、攻撃者がプログラムを利用して悪意のあるバイナリを実行することが可能になる場合があります。/var/yp
ディレクトリでの make
の実行も含まれます。プログラムはパスワード レコードを更新するため、setuid root
にインストールされていることに注意してください。make
を次のように呼び出します。
MOVE "cd /var/yp && make &> /dev/null" to command-line
CALL "CBL_EXEC_RUN_UNIT" USING command-line
length of command-line
run-unit-id
stack-size
flags
CBL_EXEC_RUN_UNIT
に渡す引数を制御できません。しかしプログラムは make
の絶対パスを指定せず、コマンド呼出しの前に環境変数をスクラブしないため、攻撃者は $PATH
変数が make
という名前の悪意のあるバイナリをポイントするように変更して、シェル プロンプトから CGI スクリプトを実行できます。さらに、プログラムは setuid root
にインストールされているため、攻撃者バージョンの make
は root
権限で実行されるようになります。pdfprint
コマンドを使用して印刷するファイルを含む一時ディレクトリを決定します。
DISPLAY "TEMP" UPON ENVIRONMENT-NAME
ACCEPT ws-temp-dir FROM ENVIRONMENT-VARIABLE
STRING "pdfprint " DELIMITED SIZE
ws-temp-dir DELIMITED SPACE
"/" DELIMITED SIZE
ws-pdf-filename DELIMITED SPACE
x"00" DELIMITED SIZE
INTO cmd-buffer
CALL "SYSTEM" USING cmd-buffer
pdfprint
の絶対パスを指定しないため、攻撃者は $PATH
変数が悪意のあるバイナリをポイントするように変更できます。さらに、DELIMITED SPACE
フレーズが ws-temp-dir
および ws-pdf-filename
における埋め込みスペースを防止する一方で、シェル メタ文字 (&&
など) が埋め込まれている可能性もあります。cmd
リクエストパラメーターを介して任意のコマンドを指定できてしまいます。
...
<cfset var="#url.cmd#">
<cfexecute name = "C:\windows\System32\cmd.exe"
arguments = "/c #var#"
timeout = "1"
variable="mycmd">
</cfexecute>
...
APPHOME
を使用してインストール先ディレクトリを特定し、指定されたディレクトリからの相対パスに基づいて初期化スクリプトを実行します。
...
final cmd = String.fromEnvironment('APPHOME');
await Process.run(cmd);
...
Example 1
のコードでは、悪意ある INITCMD
を含んだ別のパスを参照するようにシステムプロパティ APPHOME
を変更することにより、攻撃者はアプリケーションの任意のコマンドを昇格した権限で実行できます。このプログラムは環境から読み取った値の検証を行わないので、システムプロパティ APPHOME
の値を制御できれば、攻撃者はアプリケーションを操作して悪意のあるコードを実行させ、システムを支配下に置くことができます。
cmdName := request.FormValue("Command")
c := exec.Command(cmdName)
c.Run()
APPHOME
を使用してインストール先ディレクトリが決定され、指定されたディレクトリからの相対パスに基づいて初期化スクリプトが実行されます。
...
String home = System.getProperty("APPHOME");
String cmd = home + INITCMD;
java.lang.Runtime.getRuntime().exec(cmd);
...
Example 1
のコードでは、悪意ある INITCMD
を含んだ別のパスを参照するようにシステムプロパティ APPHOME
を変更することにより、攻撃者はアプリケーションの任意のコマンドを昇格した権限で実行できます。このプログラムは環境から読み取った値の検証を行わないので、システムプロパティ APPHOME
の値を制御できれば、攻撃者はアプリケーションを操作して悪意のあるコードを実行させ、システムを支配下に置くことができます。rman
ユーティリティに対するバッチファイルラッパーを使用して Oracle データベースのバックアップを開始し、その後 cleanup.bat
スクリプトを実行して一部のテンポラリ ファイルを削除できるインターフェイスを持つ Web アプリケーションのものです。スクリプト rmanDB.bat
は、実行するバックアップのタイプを指定するコマンドライン パラメーターを 1 つ受け取ります。データベースへのアクセスが制限されているため、アプリケーションは権限を持つユーザーとしてバックアップを実行します。
...
String btype = request.getParameter("backuptype");
String cmd = new String("cmd.exe /K
\"c:\\util\\rmanDB.bat "+btype+"&&c:\\util\\cleanup.bat\"")
System.Runtime.getRuntime().exec(cmd);
...
backuptype
パラメーターを検証しないことです。通常、関数 Runtime.exec()
は複数のコマンドを実行しませんが、この例のプログラムは最初に cmd.exe
シェルを実行して、Runtime.exec()
を 1 回コールするだけで複数のコマンドを実行しています。呼び出されたシェルは、2 つのアンパサンドで区切られた複数のコマンドを実行できます。攻撃者が "&& del c:\\dbms\\*.*"
という形式の文字列を渡すと、アプリケーションは、プログラムにより指定された他のコマンドとともにこのコマンドを実行します。アプリケーションはその性質上、データベースとのやり取りに必要な権限で実行されています。このため、攻撃者が挿入したコマンドも、その権限で実行されます。/var/yp
ディレクトリでの make
コマンドの実行が含まれます。
...
System.Runtime.getRuntime().exec("make");
...
Runtime.exec()
のコールを実行する前に環境をクリーンにできていないことです。攻撃者が $PATH
変数を変更して、make
という名前の悪意あるバイナリを参照させ、攻撃者の環境でプログラムが実行されるようにすると、本来のバイナリでなく悪意あるバイナリがロードされます。アプリケーションの性質上、このバイナリはシステム操作の実行に必要な権限で実行されます。つまり、攻撃者の make
もその権限で実行されるため、攻撃者がシステムを完全に制御してしまう可能性があります。
...
String[] cmds = this.getIntent().getStringArrayExtra("commands");
Process p = Runtime.getRuntime().exec("su");
DataOutputStream os = new DataOutputStream(p.getOutputStream());
for (String cmd : cmds) {
os.writeBytes(cmd+"\n");
}
os.writeBytes("exit\n");
os.flush();
...
APPHOME
を使用してインストール先ディレクトリが決定され、指定されたディレクトリからの相対パスに基づいて初期化スクリプトが実行されます。
var cp = require('child_process');
...
var home = process.env('APPHOME');
var cmd = home + INITCMD;
child = cp.exec(cmd, function(error, stdout, stderr){
...
});
...
Example 1
のコードでは、悪意ある INITCMD
を含んだ別のパスを参照するようにシステムプロパティ APPHOME
を変更することにより、攻撃者はアプリケーションの任意のコマンドを昇格した権限で実行できます。このプログラムは環境から読み取った値の検証を行わないので、システム プロパティ APPHOME
の値を制御できれば、攻撃者はアプリケーションを操作して悪意のあるコードを実行させ、システムを支配下に置くことができます。rman
ユーティリティに対するバッチファイル ラッパーを使用して Oracle データベースのバックアップを開始できるようにする管理用 Web アプリケーションのものです。スクリプト rmanDB.bat
は、実行するバックアップのタイプを指定するコマンドライン パラメーターを 1 つ受け取ります。データベースへのアクセスが制限されているため、アプリケーションは権限を持つユーザーとしてバックアップを実行します。
var cp = require('child_process');
var http = require('http');
var url = require('url');
function listener(request, response){
var btype = url.parse(request.url, true)['query']['backuptype'];
if (btype !== undefined){
cmd = "c:\\util\\rmanDB.bat" + btype;
cp.exec(cmd, function(error, stdout, stderr){
...
});
}
...
}
...
http.createServer(listener).listen(8080);
backuptype
パラメーターを、その存在を除いて検証しないことです。シェルが呼び出されると、複数のコマンドの実行が許可され、アプリケーションの特性により、データベースとの対話に必要な権限を使用して実行されるので、攻撃者が挿入する任意のコマンドもそれらの権限を使用して実行されることになります。/var/yp
ディレクトリでの make
コマンドの実行が含まれます。
...
require('child_process').exec("make", function(error, stdout, stderr){
...
});
...
make
の絶対パスを指定しておらず、child_process.exec()
の呼び出しを実行する前に環境をクリーニングできないことです。攻撃者が $PATH
変数を変更して、make
という名前の悪意あるバイナリを参照させ、攻撃者の環境でプログラムが実行されるようにすると、本来のバイナリでなく悪意あるバイナリがロードされます。アプリケーションの性質上、このバイナリはシステム操作の実行に必要な権限で実行されます。つまり、攻撃者の make
もその権限で実行されるため、攻撃者がシステムを完全に制御してしまう可能性があります。APPHOME
を使用してインストール先ディレクトリが決定され、指定されたディレクトリからの相対パスに基づいて初期化スクリプトが実行されます。
...
$home = $_ENV['APPHOME'];
$cmd = $home . $INITCMD;
system(cmd);
...
Example 1
のコードでは、悪意ある INITCMD
を含んだ別のパスを参照するようにシステムプロパティ APPHOME
を変更することにより、攻撃者はアプリケーションの任意のコマンドを昇格した権限で実行できます。このプログラムは環境から読み取った値の検証を行わないので、システムプロパティ APPHOME
の値を制御できれば、攻撃者はアプリケーションを操作して悪意のあるコードを実行させ、システムを支配下に置くことができます。rman
ユーティリティに対するバッチファイルラッパーを使用して Oracle データベースのバックアップを開始し、その後 cleanup.bat
スクリプトを実行して一部のテンポラリ ファイルを削除できるインターフェイスを持つ Web アプリケーションのものです。スクリプト rmanDB.bat
は、実行するバックアップのタイプを指定するコマンドライン パラメーターを 1 つ受け取ります。データベースへのアクセスが制限されているため、アプリケーションは権限を持つユーザーとしてバックアップを実行します。
...
$btype = $_GET['backuptype'];
$cmd = "cmd.exe /K \"c:\\util\\rmanDB.bat " . $btype . "&&c:\\util\\cleanup.bat\"";
system(cmd);
...
backuptype
パラメーターを検証しないことです。通常、関数 Runtime.exec()
は複数のコマンドを実行しませんが、この例のプログラムは最初に cmd.exe
シェルを実行して、Runtime.exec()
を 1 回コールするだけで複数のコマンドを実行しています。呼び出されたシェルは、2 つのアンパサンドで区切られた複数のコマンドを実行できます。攻撃者が "&& del c:\\dbms\\*.*"
という形式の文字列を渡すと、アプリケーションは、プログラムにより指定された他のコマンドとともにこのコマンドを実行します。アプリケーションはその性質上、データベースとのやり取りに必要な権限で実行されています。このため、攻撃者が挿入したコマンドも、その権限で実行されます。/var/yp
ディレクトリでの make
コマンドの実行が含まれます。
...
$result = shell_exec("make");
...
Runtime.exec()
のコールを実行する前に環境をクリーンにできていないことです。攻撃者が $PATH
変数を変更して、make
という名前の悪意あるバイナリを参照させ、攻撃者の環境でプログラムが実行されるようにすると、本来のバイナリでなく悪意あるバイナリがロードされます。アプリケーションの性質上、このバイナリはシステム操作の実行に必要な権限で実行されます。つまり、攻撃者の make
もその権限で実行されるため、攻撃者がシステムを完全に制御してしまう可能性があります。
...
CREATE PROCEDURE dbo.listFiles (@path NVARCHAR(200))
AS
DECLARE @cmd NVARCHAR(500)
SET @cmd = 'dir ' + @path
exec xp_cmdshell @cmd
GO
...
APPHOME
を使用してインストール先ディレクトリが決定され、指定されたディレクトリからの相対パスに基づいて初期化スクリプトが実行されます。
...
home = os.getenv('APPHOME')
cmd = home.join(INITCMD)
os.system(cmd);
...
Example 1
のコードでは、悪意ある INITCMD
を含んだ別のパスを参照するようにシステムプロパティ APPHOME
を変更することにより、攻撃者はアプリケーションの任意のコマンドを昇格した権限で実行できます。このプログラムは環境から読み取った値の検証を行わないので、システムプロパティ APPHOME
の値を制御できれば、攻撃者はアプリケーションを操作して悪意のあるコードを実行させ、システムを支配下に置くことができます。rman
ユーティリティに対するバッチファイルラッパーを使用して Oracle データベースのバックアップを開始し、その後 cleanup.bat
スクリプトを実行して一部のテンポラリ ファイルを削除できるインターフェイスを持つ Web アプリケーションのものです。スクリプト rmanDB.bat
は、実行するバックアップのタイプを指定するコマンドライン パラメーターを 1 つ受け取ります。データベースへのアクセスが制限されているため、アプリケーションは権限を持つユーザーとしてバックアップを実行します。
...
btype = req.field('backuptype')
cmd = "cmd.exe /K \"c:\\util\\rmanDB.bat " + btype + "&&c:\\util\\cleanup.bat\""
os.system(cmd);
...
backuptype
パラメーターを検証しないことです。通常、関数 Runtime.exec()
は複数のコマンドを実行しませんが、この例のプログラムは最初に cmd.exe
シェルを実行して、Runtime.exec()
を 1 回コールするだけで複数のコマンドを実行しています。呼び出されたシェルは、2 つのアンパサンドで区切られた複数のコマンドを実行できます。攻撃者が "&& del c:\\dbms\\*.*"
という形式の文字列を渡すと、アプリケーションは、プログラムにより指定された他のコマンドとともにこのコマンドを実行します。アプリケーションはその性質上、データベースとのやり取りに必要な権限で実行されています。このため、攻撃者が挿入したコマンドも、その権限で実行されます。/var/yp
ディレクトリでの make
コマンドの実行が含まれます。
...
result = os.system("make");
...
os.system()
のコールを実行する前に環境をクリーンにできていないことです。攻撃者が $PATH
変数を変更して、make
という名前の悪意あるバイナリを参照させ、攻撃者の環境でプログラムが実行されるようにすると、本来のバイナリでなく悪意あるバイナリがロードされます。アプリケーションの性質上、このバイナリはシステム操作の実行に必要な権限で実行されます。つまり、攻撃者の make
もその権限で実行されるため、攻撃者がシステムを完全に制御してしまう可能性があります。APPHOME
を使用してインストール先ディレクトリが決定され、指定されたディレクトリからの相対パスに基づいて初期化スクリプトが実行されます。
...
home = ENV['APPHOME']
cmd = home + INITCMD
Process.spawn(cmd)
...
Example 1
のコードでは、悪意ある INITCMD
を含んだ別のパスを参照するようにシステムプロパティ APPHOME
を変更することにより、攻撃者はアプリケーションの任意のコマンドを昇格した権限で実行できます。このプログラムは環境から読み取った値の検証を行わないので、システムプロパティ APPHOME
の値を制御できれば、攻撃者はアプリケーションを操作して悪意のあるコードを実行させ、システムを支配下に置くことができます。rman
ユーティリティに対するバッチファイルラッパーを使用して Oracle データベースのバックアップを開始し、その後 cleanup.bat
スクリプトを実行して一部のテンポラリ ファイルを削除できるインターフェイスを持つ Web アプリケーションのものです。スクリプト rmanDB.bat
は、実行するバックアップのタイプを指定するコマンドライン パラメーターを 1 つ受け取ります。データベースへのアクセスが制限されているため、アプリケーションは権限を持つユーザーとしてバックアップを実行します。
...
btype = req['backuptype']
cmd = "C:\\util\\rmanDB.bat #{btype} &&C:\\util\\cleanup.bat"
spawn(cmd)
...
backuptype
パラメーターを検証しないことです。Kernel.spawn
経由で呼び出されたシェルは、2 つのアンパサンドで区切られた複数のコマンドの実行を許可します。攻撃者が "&& del c:\\dbms\\*.*"
という形式の文字列を渡すと、アプリケーションは、プログラムにより指定された他のコマンドとともにこのコマンドを実行します。アプリケーションはその性質上、データベースとのやり取りに必要な権限で実行されています。このため、攻撃者が挿入したコマンドも、その権限で実行されます。/var/yp
ディレクトリでの make
コマンドの実行が含まれます。
...
system("make")
...
Kernel.system()
のコールを実行する前に環境をクリーンにできていないことです。攻撃者が $PATH
変数を変更して、make
という名前の悪意あるバイナリを参照させ、攻撃者の環境でプログラムが実行されるようにすると、本来のバイナリでなく悪意あるバイナリがロードされます。アプリケーションの性質上、このバイナリはシステム操作の実行に必要な権限で実行されます。つまり、攻撃者の make
もその権限で実行されるため、攻撃者がシステムを完全に制御してしまう可能性があります。
def changePassword(username: String, password: String) = Action { request =>
...
s'echo "${password}" | passwd ${username} --stdin'.!
...
}
APPHOME
を使用してインストール先ディレクトリが決定され、指定されたディレクトリからの相対パスに基づいて初期化スクリプトが実行されます。
...
Dim cmd
Dim home
home = Environ$("AppHome")
cmd = home & initCmd
Shell cmd, vbNormalFocus
...
Example 1
のコードでは、悪意ある INITCMD
を含んだ別のパスを参照するようにシステムプロパティ APPHOME
を変更することにより、攻撃者はアプリケーションの任意のコマンドを昇格した権限で実行できます。このプログラムは環境から読み取った値の検証を行わないので、システムプロパティ APPHOME
の値を制御できれば、攻撃者はアプリケーションを操作して悪意のあるコードを実行させ、システムを支配下に置くことができます。rman
ユーティリティに対するバッチファイルラッパーを使用して Oracle データベースのバックアップを開始し、その後 cleanup.bat
スクリプトを実行して一部のテンポラリ ファイルを削除できるインターフェイスを持つ Web アプリケーションのものです。スクリプト rmanDB.bat
は、実行するバックアップのタイプを指定するコマンドライン パラメーターを 1 つ受け取ります。データベースへのアクセスが制限されているため、アプリケーションは権限を持つユーザーとしてバックアップを実行します。
...
btype = Request.Form("backuptype")
cmd = "cmd.exe /K " & Chr(34) & "c:\util\rmanDB.bat " & btype & "&&c:\util\cleanup.bat" & Chr(34) & ";
Shell cmd, vbNormalFocus
...
backuptype
パラメーターを検証しないことです。呼び出されたシェルは、2 つのアンパサンドで区切られた複数のコマンドを実行できます。攻撃者が "&& del c:\\dbms\\*.*"
という形式の文字列を渡すと、アプリケーションは、プログラムにより指定された他のコマンドとともにこのコマンドを実行します。アプリケーションはその性質上、データベースとのやり取りに必要な権限で実行されています。このため、攻撃者が挿入したコマンドも、その権限で実行されます。/var/yp
ディレクトリでの make
コマンドの実行が含まれます。
...
$result = shell_exec("make");
...
Runtime.exec()
のコールを実行する前に環境をクリーンにできていないことです。攻撃者が $PATH
変数を変更して、make
という名前の悪意あるバイナリを参照させ、攻撃者の環境でプログラムが実行されるようにすると、本来のバイナリでなく悪意あるバイナリがロードされます。アプリケーションの性質上、このバイナリはシステム操作の実行に必要な権限で実行されます。つまり、攻撃者の make
もその権限で実行されるため、攻撃者がシステムを完全に制御してしまう可能性があります。content://my.authority/messages
content://my.authority/messages/123
content://my.authority/messages/deleted
deleted
とともに msgId コードを使用することで content://my.authority/messages/deleted
を呼び出すことができます。
// "msgId" is submitted by users
Uri dataUri = Uri.parse(WeatherContentProvider.CONTENT_URI + "/" + msgId);
Cursor wCursor1 = getContentResolver().query(dataUri, null, null, null, null);
isSecure
パラメーターを true
に設定しないで作成されます。Secure
フラグをサポートします。このフラグが設定されていると、ブラウザーは HTTPS 経由でのみ cookie を送信します。暗号化されていないチャネルで cookie を送信すると、ネットワークがスニッフィングされる可能性がありますが、secure フラグを使用することで cookie の値の機密性を保護できます。これは、cookie に個人情報が保存されている場合や、cookie によってセッション ID が送信される場合、特に重要になります。isSecure
パラメーターを true
に設定せずに cookie が作成されています。
...
Cookie cookie = new Cookie('emailCookie', emailCookie, path, maxAge, false, 'Strict');
...
isSecure
パラメーターが設定されていないアプリケーションでは、HTTPS リクエストで送信された cookie はそれ以降の HTTP リクエストでも送信されてしまいます。暗号化されていない無線接続でネットワークトラフィックをスニッフィングするのは攻撃者にとって簡単です。また、cookie (特にセッション ID が格納されている cookie) を HTTP 経由で送信すると、アプリケーションが危険にさらされる可能性があります。Secure
フラグが true
に設定されていない cookie が作成されます。Secure
フラグがサポートされています。このフラグが設定されていると、ブラウザは HTTPS 経由でのみ cookie を送信します。暗号化されていないチャネルで cookie を送信すると、ネットワークが盗聴される可能性があります。したがって、secure フラグを使用することで cookie の値の機密性を保護できます。cookie に個人情報が保存されている場合や、cookie によってセッション ID が送信される場合に特に重要になります。Secure
プロパティを設定せずにレスポンスに cookie が追加されています。
...
HttpCookie cookie = new HttpCookie("emailCookie", email);
Response.AppendCookie(cookie);
...
Secure
フラグが設定されていないアプリケーションでは、HTTPS リクエストで送信された cookie はその後に続く HTTP リクエストでも送信されてしまいます。暗号化されていない無線接続でネットワークトラフィックを盗聴するのは攻撃者にとって簡単です。つまり、cookie (特にセッションIDが格納されているcookie)をHTTP経由で送信すると、アプリケーションが危険にさらされる可能性があります。Secure
フラグを true
に設定せずに cookie を作成します。Secure
フラグがサポートされています。このフラグが設定されていると、ブラウザーは HTTPS 経由でのみ cookie を送信します。暗号化されていないチャネルで cookie を送信すると、ネットワークが盗聴される可能性があります。したがって、secure フラグを使用することで cookie の値の機密性を保護できます。これは、cookie に個人情報またはセッション ID が保存されている場合や、cookie によって CSRF トークンが送信される場合、特に重要です。Secure
フラグを設定せずに cookie がレスポンスに追加されています。
cookie := http.Cookie{
Name: "emailCookie",
Value: email,
}
http.SetCookie(response, &cookie)
...
Secure
フラグが設定されていないアプリケーションでは、HTTPS リクエストで送信された cookie はその後に続く HTTP リクエストでも送信されてしまいます。すると攻撃者は、暗号化されていないネットワーク トラフィックをスニッフィングすることによって cookie を危険にさらすことがあります。特に無線ネットワークの場合、ネットワーク トラフィックのスニッフィングは非常に簡単です。Secure
フラグが true
に設定されていない cookie が作成されます。Secure
フラグがサポートされています。このフラグが設定されていると、ブラウザーは HTTPS 経由でのみ cookie を送信します。暗号化されていないチャネルで cookie を送信すると、ネットワークが盗聴される可能性があります。したがって、secure フラグを使用することで cookie の値の機密性を保護できます。これは、cookie に個人情報が保存されている場合や、cookie によってセッション ID が送信される場合、特に重要になります。use-secure-cookie
属性によって remember-me
cookie が有効化され、暗号化されていない転送によって送信されます。
<http auto-config="true">
...
<remember-me use-secure-cookie="false"/>
</http>
Secure
フラグが設定されていないアプリケーションでは、HTTPS リクエストで送信された cookie はその後に続く HTTP リクエストでも送信されてしまいます。暗号化されていない無線接続でネットワークトラフィックを盗聴するのは攻撃者にとって簡単です。つまり、cookie (特にセッション ID が格納されている cookie) を HTTP 経由で送信すると、アプリケーションが危険にさらされる可能性があります。Secure
フラグが true
に設定されていない cookie が作成されます。Secure
フラグがサポートされています。このフラグが設定されていると、ブラウザは HTTPS 経由でのみ cookie を送信します。暗号化されていないチャネルで cookie を送信すると、ネットワークが盗聴される可能性があります。したがって、secure フラグを使用することで cookie の値の機密性を保護できます。cookie に個人情報が保存されている場合や、cookie によってセッション ID が送信される場合に特に重要になります。Secure
プロパティを true
に設定せずにレスポンスに cookie が追加されています。
res.cookie('important_cookie', info, {domain: 'secure.example.com', path: '/admin', httpOnly: true, secure: false});
Secure
フラグが設定されていないアプリケーションでは、HTTPS リクエストで送信された cookie はその後に続く HTTP リクエストでも送信されてしまいます。暗号化されていない無線接続でネットワークトラフィックを盗聴するのは攻撃者にとって簡単です。つまり、cookie (特にセッションIDが格納されているcookie)をHTTP経由で送信すると、アプリケーションが危険にさらされる可能性があります。NSHTTPCookieSecure
フラグが TRUE
に設定されていない cookie が作成されます。Secure
フラグがサポートされています。このフラグが設定されていると、ブラウザは HTTPS 経由でのみ cookie を送信します。暗号化されていないチャネルで cookie を送信すると、ネットワークが盗聴される可能性があります。したがって、secure フラグを使用することで cookie の値の機密性を保護できます。cookie に個人情報が保存されている場合や、cookie によってセッション ID が送信される場合に特に重要になります。Secure
フラグを設定せずにレスポンスに cookie が追加されています。
...
NSDictionary *cookieProperties = [NSDictionary dictionary];
...
NSHTTPCookie *cookie = [NSHTTPCookie cookieWithProperties:cookieProperties];
...
Secure
フラグが設定されていないアプリケーションでは、HTTPS リクエストで送信された cookie はその後に続く HTTP リクエストでも送信されてしまいます。暗号化されていない無線接続でネットワークトラフィックを盗聴するのは攻撃者にとって簡単です。つまり、cookie (特にセッションIDが格納されているcookie)をHTTP経由で送信すると、アプリケーションが危険にさらされる可能性があります。Secure
フラグを true
に設定せずに cookie を作成します。Secure
フラグがサポートされています。このフラグが設定されていると、ブラウザは HTTPS 経由でのみ cookie を送信します。暗号化されていないチャネルで cookie を送信すると、ネットワークが盗聴される可能性があります。したがって、secure フラグを使用することで cookie の値の機密性を保護できます。cookie に個人情報が保存されている場合や、cookie によってセッション ID が送信される場合に特に重要になります。Secure
フラグを設定せずに cookie がレスポンスに追加されています。
...
setcookie("emailCookie", $email, 0, "/", "www.example.com");
...
Secure
フラグが設定されていないアプリケーションでは、HTTPS リクエストで送信された cookie はその後に続く HTTP リクエストでも送信されてしまいます。すると攻撃者は、暗号化されていないネットワーク トラフィックをスニッフィングすることによって cookie を危険にさらすことがあります。特に無線ネットワークの場合、ネットワーク トラフィックのスニッフィングは非常に簡単です。Secure
フラグを True
に設定せずに cookie を作成します。Secure
フラグがサポートされています。このフラグが設定されていると、ブラウザは HTTPS 経由でのみ cookie を送信します。暗号化されていないチャネルで cookie を送信すると、ネットワークが盗聴される可能性があります。したがって、secure フラグを使用することで cookie の値の機密性を保護できます。cookie に個人情報またはセッション ID が保存されている場合や、cookie によって CSRF トークンが送信される場合に特に重要になります。Secure
フラグを設定せずに cookie がレスポンスに追加されています。
from django.http.response import HttpResponse
...
def view_method(request):
res = HttpResponse()
res.set_cookie("emailCookie", email)
return res
...
Secure
フラグが設定されていないアプリケーションでは、HTTPS リクエストで送信された cookie はその後に続く HTTP リクエストでも送信されてしまいます。すると攻撃者は、暗号化されていないネットワーク トラフィックをスニッフィングすることによって cookie を危険にさらすことがあります。特に無線ネットワークの場合、ネットワーク トラフィックのスニッフィングは非常に簡単です。Secure
フラグが true
に設定されていない cookie が作成されます。Secure
フラグがサポートされています。このフラグが設定されていると、ブラウザーは HTTPS 経由でのみ cookie を送信します。暗号化されていないチャネルで cookie を送信すると、ネットワークが盗聴される可能性があります。したがって、secure フラグを使用することで cookie の値の機密性を保護できます。これは、cookie に個人情報が保存されている場合や、cookie によってセッション ID が送信される場合、特に重要になります。Secure
フラグを設定せずにレスポンスに cookie が追加されています。
Ok(Html(command)).withCookies(Cookie("sessionID", sessionID, secure = false))
Secure
フラグが設定されていないアプリケーションでは、HTTPS リクエストで送信された cookie はその後に続く HTTP リクエストでも送信されてしまいます。暗号化されていない無線接続でネットワークトラフィックを盗聴するのは攻撃者にとって簡単です。つまり、cookie (特にセッション ID が格納されている cookie) を HTTP 経由で送信すると、アプリケーションが危険にさらされる可能性があります。NSHTTPCookieSecure
フラグが TRUE
に設定されていない cookie が作成されます。Secure
フラグがサポートされています。このフラグが設定されていると、ブラウザーは HTTPS 経由でのみ cookie を送信します。暗号化されていないチャネルで cookie を送信すると、ネットワークが盗聴される可能性があります。したがって、secure フラグを使用することで cookie の値の機密性を保護できます。これは、cookie に個人情報が保存されている場合や、cookie によってセッション ID が送信される場合、特に重要になります。Secure
フラグを設定せずにレスポンスに cookie が追加されています。
...
let properties = [
NSHTTPCookieDomain: "www.example.com",
NSHTTPCookiePath: "/service",
NSHTTPCookieName: "foo",
NSHTTPCookieValue: "bar"
]
let cookie : NSHTTPCookie? = NSHTTPCookie(properties:properties)
...
Secure
フラグが設定されていないアプリケーションでは、HTTPS リクエストで送信された cookie はその後に続く HTTP リクエストでも送信されてしまいます。暗号化されていない無線接続でネットワークトラフィックを盗聴するのは攻撃者にとって簡単です。つまり、cookie (特にセッション ID が格納されている cookie) を HTTP 経由で送信すると、アプリケーションが危険にさらされる可能性があります。HttpOnly
フラグを true
に設定していません。HttpOnly
cookie プロパティを設定すると、クライアント側のスクリプトが cookie にアクセスすることを防止できます。Cross-Site Scripting 攻撃では多くの場合、セッション ID や Authentication トークンを盗み出すために cookie へアクセスします。HttpOnly
フラグを有効にしないと、攻撃者は容易にユーザーの cookie にアクセスできます。HttpOnly
プロパティが設定されずに cookie が作成されています。
HttpCookie cookie = new HttpCookie("emailCookie", email);
Response.AppendCookie(cookie);
HttpOnly
フラグを true
に設定していません。HttpOnly
を設定すると、クライアント側のスクリプトが cookie にアクセスすることを防止できます。Cross-Site Scripting 攻撃では多くの場合、セッション ID や Authentication トークンを盗み出すために cookie へアクセスします。HttpOnly
を有効にしないと、攻撃者は容易にユーザーの cookie にアクセスできます。HttpOnly
プロパティが設定されずに cookie が作成されています。
cookie := http.Cookie{
Name: "emailCookie",
Value: email,
}
...
HttpOnly
フラグを true
に設定していません。HttpOnly
cookie プロパティを設定すると、クライアント側のスクリプトが cookie にアクセスすることを防止できます。Cross-Site Scripting 攻撃では多くの場合、セッション ID や Authentication トークンを盗み出すために cookie へアクセスします。HttpOnly
フラグを有効にしないと、攻撃者は容易にユーザーの cookie にアクセスできます。HttpOnly
プロパティが設定されずに cookie が作成されています。
javax.servlet.http.Cookie cookie = new javax.servlet.http.Cookie("emailCookie", email);
// Missing a call to: cookie.setHttpOnly(true);
HttpOnly
フラグを true
に設定していません。HttpOnly
cookie プロパティを設定すると、クライアント側のスクリプトが cookie にアクセスすることを防止できます。Cross-Site Scripting 攻撃では多くの場合、セッション ID や Authentication トークンを盗み出すために cookie へアクセスします。HttpOnly
フラグを有効にしないと、攻撃者は容易にユーザーの cookie にアクセスできます。httpOnly
プロパティが設定されずに cookie が作成されています。
res.cookie('important_cookie', info, {domain: 'secure.example.com', path: '/admin'});
HttpOnly
フラグを true
に設定していません。HttpOnly
cookie プロパティを設定すると、クライアント側のスクリプトが cookie にアクセスすることを防止できます。Cross-Site Scripting 攻撃では多くの場合、セッション ID や Authentication トークンを盗み出すために cookie へアクセスします。HttpOnly
フラグを有効にしないと、攻撃者は容易にユーザーの cookie にアクセスできます。HttpOnly
プロパティが設定されずに cookie が作成されています。
setcookie("emailCookie", $email, 0, "/", "www.example.com", TRUE); //Missing 7th parameter to set HttpOnly
HttpOnly
フラグを True
に設定していません。HttpOnly
cookie プロパティを設定すると、クライアント側のスクリプトが cookie にアクセスすることを防止できます。Cross-Site Scripting 攻撃では多くの場合、セッション ID や Authentication トークンを盗み出すために cookie にアクセスします。HttpOnly
が有効に設定されていない場合、攻撃者は容易にユーザーの cookie にアクセスできます。HttpOnly
プロパティが設定されずに cookie が作成されています。
from django.http.response import HttpResponse
...
def view_method(request):
res = HttpResponse()
res.set_cookie("emailCookie", email)
return res
...
HttpOnly
フラグを true
に設定していません。HttpOnly
cookie プロパティを設定すると、クライアント側のスクリプトが cookie にアクセスすることを防止できます。Cross-Site Scripting 攻撃では多くの場合、セッション ID や Authentication トークンを盗み出すために cookie へアクセスします。HttpOnly
フラグを有効にしないと、攻撃者は容易にユーザーの cookie にアクセスできます。HttpOnly
プロパティが設定されずに cookie が作成されています。
Ok(Html(command)).withCookies(Cookie("sessionID", sessionID, httpOnly = false))
HttpOnly
フラグを true
に設定していません。HttpOnly
cookie プロパティを設定すると、クライアント側のスクリプトが cookie にアクセスすることを防止できます。Cross-Site Scripting 攻撃では多くの場合、セッション ID や Authentication トークンを盗み出すために cookie へアクセスします。HttpOnly
フラグを有効にしないと、攻撃者は容易にユーザーの cookie にアクセスできます。HttpOnly
フラグを true
に設定せずにセッション cookie を作成します。
server.servlet.session.cookie.http-only=false
HttpOnly
フラグを true
に設定していません。HttpOnly
cookie プロパティを設定すると、クライアント側のスクリプトが cookie にアクセスすることを防止できます。Cross-Site Scripting 攻撃では多くの場合、セッション ID や Authentication トークンを盗み出すために cookie へアクセスします。HttpOnly
フラグを有効にしないと、攻撃者は容易にユーザーの cookie にアクセスできます。HttpOnly
フラグを true
に設定せずにセッション cookie を作成します。
session_set_cookie_params(0, "/", "www.example.com", true, false);
HttpOnly
フラグを true
に設定できません。HttpOnly
cookie プロパティを設定すると、クライアント側のスクリプトが cookie にアクセスすることを防止できます。Cross-Site Scripting 攻撃では多くの場合、セッション ID や Authentication トークンを盗み出すために cookie にアクセスします。HttpOnly
が有効に設定されていない場合、攻撃者は容易にユーザーの cookie にアクセスできます。HttpOnly
プロパティを設定せず、セッション cookie を明示的に設定します。
...
MIDDLEWARE = (
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'csp.middleware.CSPMiddleware',
'django.middleware.security.SecurityMiddleware',
...
)
...
SESSION_COOKIE_HTTPONLY = False
...