X-Git-Url: http://wien.tomnetworks.com/gitweb/?a=blobdiff_plain;f=mono%2Fmetadata%2Fsecurity-core-clr.c;h=f874043e15b6e58f423ea2752fdcc12795a4fbe6;hb=56ad8f4e5dfb8198e4671f631a3103b1e8b83dd3;hp=de9ec6a79c993c20b6f1f3f08893461f1226d722;hpb=487cc2845f033e5b2ba41d7edb6486ffc8f33b97;p=mono.git diff --git a/mono/metadata/security-core-clr.c b/mono/metadata/security-core-clr.c index de9ec6a79c9..f874043e15b 100644 --- a/mono/metadata/security-core-clr.c +++ b/mono/metadata/security-core-clr.c @@ -6,6 +6,7 @@ * Sebastien Pouliot * * Copyright 2007-2010 Novell, Inc (http://www.novell.com) + * Licensed under the MIT license. See LICENSE file in the project root for full license information. */ #include @@ -122,30 +123,21 @@ mono_security_core_clr_is_platform_image (MonoImage *image) #ifndef DISABLE_SECURITY +/* Class lazy loading functions */ +static GENERATE_GET_CLASS_WITH_CACHE (security_critical, System.Security, SecurityCriticalAttribute) +static GENERATE_GET_CLASS_WITH_CACHE (security_safe_critical, System.Security, SecuritySafeCriticalAttribute) + static MonoClass* security_critical_attribute (void) { - static MonoClass *klass = NULL; - - if (!klass) { - klass = mono_class_from_name (mono_defaults.corlib, "System.Security", - "SecurityCriticalAttribute"); - } - g_assert (klass); - return klass; + return mono_class_get_security_critical_class (); } static MonoClass* security_safe_critical_attribute (void) { - static MonoClass *klass = NULL; + return mono_class_get_security_safe_critical_class (); - if (!klass) { - klass = mono_class_from_name (mono_defaults.corlib, "System.Security", - "SecuritySafeCriticalAttribute"); - } - g_assert (klass); - return klass; } /* sometime we get a NULL (not found) caller (e.g. get_reflection_caller) */ @@ -633,34 +625,38 @@ get_method_access_exception (const char *format, MonoMethod *caller, MonoMethod * Transparent code cannot access to Critical fields and can only use * them if they are visible from it's point of view. * - * A FieldAccessException is thrown if the field is cannot be accessed. + * Returns TRUE if acess is allowed. Otherwise returns FALSE and sets @error to a FieldAccessException if the field is cannot be accessed. */ -void -mono_security_core_clr_ensure_reflection_access_field (MonoClassField *field) +gboolean +mono_security_core_clr_ensure_reflection_access_field (MonoClassField *field, MonoError *error) { + mono_error_init (error); MonoMethod *caller = get_reflection_caller (); /* CoreCLR restrictions applies to Transparent code/caller */ if (mono_security_core_clr_method_level (caller, TRUE) != MONO_SECURITY_CORE_CLR_TRANSPARENT) - return; + return TRUE; if (mono_security_core_clr_get_options () & MONO_SECURITY_CORE_CLR_OPTIONS_RELAX_REFLECTION) { if (!mono_security_core_clr_is_platform_image (mono_field_get_parent(field)->image)) - return; + return TRUE; } /* Transparent code cannot [get|set]value on Critical fields */ if (mono_security_core_clr_class_level (mono_field_get_parent (field)) == MONO_SECURITY_CORE_CLR_CRITICAL) { - mono_raise_exception (get_field_access_exception ( + mono_error_set_exception_instance (error, get_field_access_exception ( "Transparent method %s cannot get or set Critical field %s.", caller, field)); + return FALSE; } /* also it cannot access a fields that is not visible from it's (caller) point of view */ if (!check_field_access (caller, field)) { - mono_raise_exception (get_field_access_exception ( + mono_error_set_exception_instance (error, get_field_access_exception ( "Transparent method %s cannot get or set private/internal field %s.", caller, field)); + return FALSE; } + return TRUE; } /* @@ -670,34 +666,38 @@ mono_security_core_clr_ensure_reflection_access_field (MonoClassField *field) * Transparent code cannot call Critical methods and can only call them * if they are visible from it's point of view. * - * A MethodAccessException is thrown if the field is cannot be accessed. + * If access is allowed returns TRUE. Returns FALSE and sets @error to a MethodAccessException if the field is cannot be accessed. */ -void -mono_security_core_clr_ensure_reflection_access_method (MonoMethod *method) +gboolean +mono_security_core_clr_ensure_reflection_access_method (MonoMethod *method, MonoError *error) { + mono_error_init (error); MonoMethod *caller = get_reflection_caller (); /* CoreCLR restrictions applies to Transparent code/caller */ if (mono_security_core_clr_method_level (caller, TRUE) != MONO_SECURITY_CORE_CLR_TRANSPARENT) - return; + return TRUE; if (mono_security_core_clr_get_options () & MONO_SECURITY_CORE_CLR_OPTIONS_RELAX_REFLECTION) { if (!mono_security_core_clr_is_platform_image (method->klass->image)) - return; + return TRUE; } /* Transparent code cannot invoke, even using reflection, Critical code */ if (mono_security_core_clr_method_level (method, TRUE) == MONO_SECURITY_CORE_CLR_CRITICAL) { - mono_raise_exception (get_method_access_exception ( + mono_error_set_exception_instance (error, get_method_access_exception ( "Transparent method %s cannot invoke Critical method %s.", caller, method)); + return FALSE; } /* also it cannot invoke a method that is not visible from it's (caller) point of view */ if (!check_method_access (caller, method)) { - mono_raise_exception (get_method_access_exception ( + mono_error_set_exception_instance (error, get_method_access_exception ( "Transparent method %s cannot invoke private/internal method %s.", caller, method)); + return FALSE; } + return TRUE; } /* @@ -735,19 +735,20 @@ can_avoid_corlib_reflection_delegate_optimization (MonoMethod *method) /* * mono_security_core_clr_ensure_delegate_creation: * - * Return TRUE if a delegate can be created on the specified method. - * CoreCLR also affect the binding, so throwOnBindFailure must be - * FALSE to let this function return (FALSE) normally, otherwise (if - * throwOnBindFailure is TRUE) it will throw an ArgumentException. + * Return TRUE if a delegate can be created on the specified + * method. CoreCLR can also affect the binding, this function may + * return (FALSE) and set @error to an ArgumentException. * - * A MethodAccessException is thrown if the specified method is not + * @error is set to a MethodAccessException if the specified method is not * visible from the caller point of view. */ gboolean -mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, gboolean throwOnBindFailure) +mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, MonoError *error) { MonoMethod *caller; + mono_error_init (error); + /* note: mscorlib creates delegates to avoid reflection (optimization), we ignore those cases */ if (can_avoid_corlib_reflection_delegate_optimization (method)) return TRUE; @@ -759,13 +760,10 @@ mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, gboolean th /* otherwise it (as a Transparent caller) cannot create a delegate on a Critical method... */ if (mono_security_core_clr_method_level (method, TRUE) == MONO_SECURITY_CORE_CLR_CRITICAL) { - /* but this throws only if 'throwOnBindFailure' is TRUE */ - if (!throwOnBindFailure) - return FALSE; - - mono_raise_exception (get_argument_exception ( + mono_error_set_exception_instance (error, get_argument_exception ( "Transparent method %s cannot create a delegate on Critical method %s.", caller, method)); + return FALSE; } if (mono_security_core_clr_get_options () & MONO_SECURITY_CORE_CLR_OPTIONS_RELAX_DELEGATE) { @@ -775,9 +773,10 @@ mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, gboolean th /* also it cannot create the delegate on a method that is not visible from it's (caller) point of view */ if (!check_method_access (caller, method)) { - mono_raise_exception (get_method_access_exception ( + mono_error_set_exception_instance (error, get_method_access_exception ( "Transparent method %s cannot create a delegate on private/internal method %s.", caller, method)); + return FALSE; } return TRUE; @@ -1058,19 +1057,24 @@ mono_security_core_clr_require_elevated_permissions (void) return FALSE; } -void -mono_security_core_clr_ensure_reflection_access_field (MonoClassField *field) +gboolean +mono_security_core_clr_ensure_reflection_access_field (MonoClassField *field, MonoError *error) { + mono_error_init (error); + return TRUE; } void -mono_security_core_clr_ensure_reflection_access_method (MonoMethod *method) +mono_security_core_clr_ensure_reflection_access_method (MonoMethod *method, MonoError *error) { + mono_error_init (error); + return TRUE; } gboolean -mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, gboolean throwOnBindFailure) +mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, MonoError *error) { + mono_error_init (error); return TRUE; }