Whoops!"; } } public static void Main { /* Chính bản thân phương thức sẽ gọi security permission Deny cho unmanaged code, và sẽ ghi chồng lên Assert permission trong stack frame.*/ Secur
Trang 1Console.WriteLine("Attempting to call unmanaged code with permission."); NativeMethods.puts("Hello World!");
NativeMethods._flushall();
Console.WriteLine("Called unmanaged code with permission.");
}
catch (SecurityException)
{
Console.WriteLine("Caught Security Exception attempting to call unmanaged code Whoops!");
}
}
public static void Main()
{
/* Chính bản thân phương thức sẽ gọi security permission Deny cho unmanaged code, và sẽ ghi chồng lên Assert permission trong stack frame.*/
SecurityPermission perm = new
SecurityPermission(SecurityPermissionFlag.Unmanage dCode);
perm.Assert();
CallUnmanagedCodeWithoutPermission();
/* Chính phương thức sẽ gọi security permission Assert cho unmanaged code, và
sẽ ghi chồng lên Deny permission trong stack frame.*/
perm.Deny();
CallUnmanagedCodeWithPermission();
}
}
Output
Attempting to call unmanaged code without permission
Caught Security Exception attempting to call unmanaged code
Attempting to call unmanaged code with permission
Hello World!
Called unmanaged code with permission
Trang 2Ví dụ 2
// Declaratively: Sử dụng những thuộc tính an toàn của permission
// DeclarativeSecurity.cs
using System;
using System.Security;
using System.Security.Permissions;
using System.Runtime.InteropServices;
class NativeMethods
{
/* Gọi đến unmanaged code Thi hành phương thức đòi hỏi UnmanagedCode
security permission Nếu không có permission, thì sẽ đưa ra một ngoại lệ
SecurityException:*/
[DllImport("msvcrt.dll")]
public static extern int puts(string str);
[DllImport("msvcrt.dll")]
internal static extern int _flushall();
}
class MainClass
{
/*Security permission được gắn vào phương thức này sẽ từ chối permission của UnmanagedCode từ những thiết lập của những permission hiện tại trong khi lời gọi phương thức có hiệu lực, thậm chí khi phương thức
CallUnmanagedCodeWithoutPermission được gọi từ stack frame đã sẵn sàng gọi quyền cho unmanaged code, thì ta vẫn không thể gọi cái mã này, bởi vì hàm này được gắn với Deny permission cho unmanaged code, permission được ghi chồng.*/ [SecurityPermission(SecurityAction.Deny, Flags =
SecurityPermissionFlag.UnmanagedCode)]
private static void CallUnmanagedCodeWithoutPermission()
{
try
{
Console.WriteLine("Attempting to call unmanaged code without permission."); NativeMethods.puts("Hello World!");
Trang 3NativeMethods._flushall();
Console.WriteLine("Called unmanaged code without permission Whoops!"); }
catch (SecurityException)
{
Console.WriteLine("Caught Security Exception attempting to call unmanaged code.");
}
}
/*security permission được gắn vào phương thức này sẽ bắt buộc kiểm tra thực thi cho unmanaged code permission bất cứ khi nào phương thức được gọi Nếut lời gọi không có unmanaged code permission, thì lời gọi sẽ tạo ra một Security
Exception Thậm chí khi phương thức CallUnmanagedCodeWithPermission được gọi từ một stack frame sẵn sàng gọi Deny cho unmanaged code, nó sẽ không ngăn chặn ta từ lời gọi Bởi vì phương thức này được gắn với Assert permission cho unmanaged code, permission đã được ghi chồng.*/
[SecurityPermission(SecurityAction.Assert, Flags =
SecurityPermissionFlag.UnmanagedCode)]
private static void CallUnmanagedCodeWithPermission()
{
try
{
Console.WriteLine("Attempting to call unmanaged code with permission."); NativeMethods.puts("Hello World!");
NativeMethods._flushall();
Console.WriteLine("Called unmanaged code with permission.");
}
catch (SecurityException)
{
Console.WriteLine("Caught Security Exception attempting to call unmanaged code Whoops!");
}
}
Trang 4public static void Main()
{
SecurityPermission perm = new
SecurityPermission(SecurityPermissionFlag.Unmanage dCode);
/* Chính bản thân phương thức được gắn với security permission Deny cho
unmanaged code sẽ ghi chồng lên Assert permission trong stack frame này.*/ perm.Assert();
CallUnmanagedCodeWithoutPermission();
/* Phương thức được gắn với security permission Assert cho unmanaged code sẽ ghi chồng lên Deny permission trong stack frame.*/
perm.Deny();
CallUnmanagedCodeWithPermission();
}
}
Output
Attempting to call unmanaged code without permission
Caught Security Exception attempting to call unmanaged code
Attempting to call unmanaged code with permission
Hello World!
Called unmanaged code with permission
Security and Performance
Hệ thống bảo mật của bộ khung NET có khả năng ngăn chặn những đoạn mã có tính chất gây nguy hiểm được tải xuống từ mạng nằm trong máy tính Tuy nhiên những công việc kiểm tra an toàn này có thể không được thực hiện, thậm chí khi đoạn mã không bao giờ đưa ra một ngoại lệ an toàn bảo mật nào
Thông thường ngôn ngữ thi hành chung ( common language runtime ) sẽ xác minh lời gọi từ những đoạn mã của một phương thức không được quản lý, những
phương thức này không có những đoạn mã quản lý truy cập permission Điều này
có thể sẽ gây rất nhiều khó khăn cho ứng dụng khi thực hiện những lời gọi những đoạn mã không được quản lý SuppressUnmanagedCodeSecurityAttribute sẽ thay
Trang 5thế cho vần đề mặc định này Khi một phương thức được gắn thuộc tính này ( SuppressUnmanagedCodeSecurityAttribute ), yêu cầu bảo vệ an toàn được kiểm tra khi mà chương trình thực hiện gọi phương thức được nạp vào trình điều khiển của common language runtime
Security Note
Khi dùng SuppressUnmanagedCodeSecurityAttribute ta cần phải thận trọng hơn để đảm bảo rằng sẽ không có một lỗi an toàn nào trong chương trình của ta ( code )
Ví dụ 3:
// SuppressSecurity.cs
using System;
using System.Security;
using System.Security.Permissions;
using System.Runtime.InteropServices;
class NativeMethods
{
/* Gọi đến unmanaged code Thi hành phương thức đòi hỏiUnmanagedCode
security permission Nếu không có permission này thì sẽ đưa ra
SecurityException:*/
/* Chú ý: SuppressUnmanagedCodeSecurityAttribute không thể kiểm tra
UnmanagedCode permission lúc thi hành ! */
[SuppressUnmanagedCodeSecurityAttribute()]
[DllImport("msvcrt.dll")]
internal static extern int puts(string str);
[SuppressUnmanagedCodeSecurityAttribute()]
[DllImport("msvcrt.dll")]
internal static extern int _flushall();
}
class MainClass
{
/* security permission được gắn vào phương thức này sẽ hủy UnmanagedCode permission từ những thết lập permissions cho khoảng thời gian gọi đến phương
Trang 6thức này Dù là phương thức CallUnmanagedCodeWithoutPermission được gọi từ một stack frame sẵn sàng gọi Assert cho unmanaged code, ta vẫn không thể gọi cái
mã này Bởi vì phương thức này đã được gắn Deny permission cho unmanaged code, permission đâ được ghi chồng Tuy nhiên do ta dùng
SuppressUnmanagedCodeSecurityAttribute ở đây, ta vẫn có thể gọi unmanaged methods thành công Cái mã này sẽ dùng chế độ kiểm tra an toàn khác để đẩm bảo
ta không mắc phải lỗ hổng an toàn bảo mật.*/
[SecurityPermission(SecurityAction.Deny, Flags =
SecurityPermissionFlag.UnmanagedCode)]
private static void CallUnmanagedCodeWithoutPermission()
{
try
{
/* The UnmanagedCode security check is disbled on the call below Tuy nhiên, lời gọi unmanaged chỉ hiển thị UI Security sẽ được đảm bảo vì chỉ cho phép gọi nếu
có một UI permission.*/
UIPermission uiPermission =
new UIPermission(PermissionState.Unrestricted);
uiPermission.Demand();
Console.WriteLine("Attempting to call unmanaged code without UnmanagedCode permission.");
NativeMethods.puts("Hello World!");
NativeMethods._flushall();
Console.WriteLine("Called unmanaged code without UnmanagedCode