Как предотвратить ненадежный строковый параметр в C # - PullRequest
0 голосов
/ 20 декабря 2010

По соображениям безопасности я не хочу, чтобы конкретный метод получал строки времени, не относящиеся к программированию или не компилятору, как я могу это сделать?

readonly String OK_STR = "some text";
String BAD_STR = "another text";

public void SetSecureStr(String str)
{
    //Use the string for security purpose
}

//Somewhere in the code
SetSecureStr(OK_STR); //Accepted
SetSecureStr(OK_STR + "Programmer passed this staticlly!"); //Accepted (If not possible to implement, forget about it)
SetSecureStr(BAD_STR); //Throw exception, BAD_STR is modifiable
SetSecureStr(OK_STR + untrustedVar); //Throw exception, concatenation with modifiable
SetSecureStr(String.Format("{0}", OK_STR)); //Throw exception, not const

Ответы [ 3 ]

1 голос
/ 20 декабря 2010

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

В качестве грубой проверки вы можете проверить, является ли она интернированной , поскольку все литералы будут интернированы автоматически через ldstr;но учтите, что вы также можете явно интернировать, так что это не на 100% безопасно.

И, конечно, в любом случае вопрос , который задают , если этоСтрока происходит где-то еще как литерал (не связанный с этим кодом), ему все равно можно доверять.Я полагаю, что белый список безопаснее ...

Белый список может быть простым:

private static readonly HashSet<string> whiteList = new HashSet<string> {
    "good", "more good"
};
... check via whiteList.Contains(s)

, но учтите, что он все еще может изменяться во время выполнения (с помощью отражения при необходимости).

0 голосов
/ 20 декабря 2010

Я наконец-то нашел решение, которое является гибридом двух ранее предложенных ответов:

public class SqlQuery
{
    private SqlQuery() { }

    private static UInt32 sqlQueriesCount = 0;

    public static UInt32 INBOUND_UPDATE_CALLBACK_NUM = sqlQueriesCount++;
    public static UInt32 INBOUND_UPDATE_DEST_ADDR_SUBUNIT = sqlQueriesCount++;
    public static UInt32 INBOUND_UPDATE_DEST_BEARER_TYPE = sqlQueriesCount++;
    //...etc

    private static readonly Dictionary<UInt32, String> queries = new Dictionary<UInt32, String>
    {
        {SqlQuery.INBOUND_UPDATE_CALLBACK_NUM, "UPDATE inbound SET callbackNum = ? WHERE id = ?"},
        {SqlQuery.INBOUND_UPDATE_DEST_ADDR_SUBUNIT, "UPDATE inbound SET destAddrSubunit = ? WHERE id = ?"},
        {SqlQuery.INBOUND_UPDATE_DEST_BEARER_TYPE, "UPDATE inbound SET destBearerType = ? WHERE id = ?"},
        //...etc
    };

    public static String GetQueryText(UInt32 queryKey)
    {
        String query = null;
        if (SqlQuery.queries.TryGetValue(queryKey, out query) == false)
        {
        throw new ArgumentOutOfRangeException(String.Format("Query must be paramerized query stored within SqlQuery class, provided queryKey: {0}", queryKey));
        }
        return query;
    }
}

Использование:

OdbcCommand cmd = new OdbcCommand(SqlQuery.GetQueryText(SqlQuery.INBOUND_UPDATE_CALLBACK_NUM), con);
0 голосов
/ 20 декабря 2010

Вместо того, чтобы принимать строковые значения, нумеруйте все свои строки и передайте число:

string[] good_strings = {"some text"};
public void SetSecureStr(int stringno)
{
    string s = good_strings[stringno];
}

Вычисленные строки не будут поддерживаться при таком подходе.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...