Как эффективно создавать сборки F # для частичного доверия?

Есть ли у кого-нибудь опыт работы с кодом F # в сценариях частичного доверия? Как и в случае создания сборок с [<AllowPartiallyTrustedCallers>]?

Я работаю над несколькими проектами, которые нам нужно выполнить с частичным доверием, и мы пытаемся использовать Правила безопасности Уровня 2 (http://msdn.microsoft.com/en-us/library/dd233102.aspx). На практике для наших автономных сборок это просто - просто поместите атрибут; но иногда наши сборки ссылаются на сторонние библиотеки DLL, которые не являются аннотированными и предполагаются "SecurityCritical". Здесь он становится "интересным".

Сработав с ним последние пару дней, проблема связана с F #. Политика безопасности .NET предполагает, что вы будете аннотировать типы/методы с помощью [<SecuritySafeCritical>], если они ссылаются или вызывают код "SecurityCritical", который, как оказалось, является большей частью кода на NuGet, потому что это то, что по умолчанию. Теперь, в F #, это работает нормально, пока вы не начнете использовать закрытие. Вы не можете:

namespace Foo

open System.Security

[<assembly: AllowPartiallyTrustedCallers>]
[<assembly: SecurityRules(SecurityRuleSet.Level2)>]
do()

[<SecurityCritical>]
module C =
    let get () = [ 1 .. 10 ]

[<SecuritySafeCritical>]
module M =

    let foo () =
        seq {
            for i in 1 .. 10 do
                yield!
                    C.get ()
                    |> Seq.filter (fun x -> x % 2 = 0)
        }

Эта сборка не проходит проверку SecAnnotate.exe, потому что компилятор F # поднимает замыкание на отдельный тип, который теперь НЕ был аннотирован с помощью [<SecuritySafeCritical>], по умолчанию используется Transparent, но ссылается на некоторый критический код, который является ошибкой.

Это звучит как незначительное ограничение, но мне стоило много часов изменять код, чтобы избежать закрытия и удовлетворить ограничения SecAnnotate. Возможно, F # может распространять атрибуты безопасности на типы закрытий, которые он создает? Есть ли еще один простой способ, которым я не хватает?

Ответ 1

Вы можете применить SecurityCritical как атрибут уровня сборки:

[<assembly: SecurityCritical>]

Лучший подход, хотя предполагается, что вы просто пишете "простое" сборку F #, то есть тот, который не делает ничего, что требует специальной защиты (например, P/Invoke), заменит:

[<assembly: AllowPartiallyTrustedCallers>]

с

[<assembly: SecurityTransparent>]

Страница MSDN для SecurityTransparentAttribute говорит:

Указывает, что сборка не может вызвать повышение привилегий.

Прозрачные сборки могут быть доступны из частично доверенного кода и не могут предоставлять доступ к защищенным ресурсам или функциям. Код в сборке не разрешает подавлять проверки безопасности доступа к коду и не может вызывать повышение привилегий.

Версия FSHarp.Core F # 3.0 также использует этот атрибут по той же причине.

Ссылки на дополнительную информацию: