Introduction.
Moving beyond the small stand-alone applications that are content
functioning with default permissions, there may be times when your program needs
to access resources that you prefer to restrict other external assemblies from
having direct access to. How you restrict access to your library modules and
resources requires that you understand the pros and cons in the security process
used.
What is Assert?
Assert is a security action that is evaluated at run time. Code Access
Permission classes and Permission Sets support a method called Assert. Using the
Assert method to control access to resources or actions will allow your code to
perform actions that it normally has permission to perform and will allow other
callers up stream in the call stack to have access that they would not normally
have. However, the key to successfully using Assert is to understand how it
affects the security checks that the code makes.
Performance.
The security mechanism of the run time walks up the call stack when
performing security checks on a demanded restriction. The run time's security
mechanism checks permissions of each caller in the stack that calls the
operation demanding restricted access. Since the run time inspects permissions
of all callers up the stack, demanding permissions can create a considerable
overhead in larger programs.
For example, if you have a library module that accesses a restricted resource or
performs a restricted action that requires or demands a specific permission from
its caller before granting this access, and during the course of your program
you request multiple accesses to the restricted method, each time the method is
requested, the security mechanism has to walk up the call stack checking the
permissions of each of its callers. Depending on how many callers are in the
stack, this can be a considerable number of permission evaluations. If your code
accesses the method 10 times and there are 10 callers currently above it in the
call stack, there will be 100 permission evaluations performed.
Using Assert in your library to assert the specific permission, you can
eliminate the further walks up the call stack. This can greatly reduce the
number of evaluations that would normally be performed up the call stack. To do
this would also require your code to have both the permission to perform the
request being made and also the permission to make assertions.
The figure below demonstrates file permissions and how assert affects the call
stack:
In the above image, we will assume that assembly 2 is your DLL module. Assembly
2 has permission to read all files on the drive, and assembly 3 can only read
files with an XML extension. Assembly 1 has not been granted file IO
permissions. Assembly 1 makes a call to our library module (assembly 2), which
in turn calls assembly 3. Under normal circumstances, when assembly 3 tries to
read an XML file, the run times security mechanism will check the permissions of
its callers (assembly 2 and assembly 1). This call would then fail and throw a
security exception because assembly 1 which originated the call does not have
the proper permissions.
Assembly 2 does have permissions to read XML files as well as all other files.
We could then have our library module assert its permission to read files. When
assembly number 3 tries to read a XML file, the required permissions to do so
will cause the security mechanism to make its walk up the stack checking that
each of its callers have the proper permission. The security mechanism of the
run time will then walk up the call stack. Since assembly number 2 uses
assertion on the same permission type (FileIOPermissions), the call stack walk
stops at assembly number 2. This is how the number of permission evaluations can
be reduced. Your gain will vary depending on the number of callers and the
number of accesses.
Being Careful With Assert.
In the scenario above, the possibility for a performance gain can be
realized. If you look at the picture closely though, you see that assembly
number 1 was not granted file IO permissions at all. The normal, full walk up
the call stack would have caught this and caused a Security Exception. When
assembly number 2 asserts its file permissions, it is passing on its permissions
to all its callers up stream in the call stack and the security checks for this
asserted permission is checked no further up the stack than the assembly making
the assertion.
Using the Assert method on a permission object will let others call your code
and access a method that the callers would not normally have permission to
access. Assertion can have its advantages such as performance gains, but be
careful that the actions and resources you are providing access to are handled
using additional security features. Evaluate the security holes that could be
opened up through the use of assertion.