Pull to refresh

Исключительно простые задачи по AppSec .NET

Reading time5 min
Views11K
Предлагаю всем размять мозг после выходных и начать рабочую неделю с простых, на первый взгляд, задачек по программированию на C#. Возможно эти задачи заставят вас посмотреть на код своих проектов с новой стороны, так как все они касаются сумрачной области – области безопасности приложений, Application Security. Про AppSec и платформу .NET пишут не много, говорят еще меньше, некоторые вообще считают, что использование любого managed языка, магическим образом делает приложение защищенным. Это положение дел я пытаюсь исправить, рассказывая на конференциях про различные аспекты безопасности .NET платформы. Так на этой недели, в четверг, наше сообщество SPB .NET Community проводит митап в Санкт-Петербурге полностью посвящённый вопросам разработки защищённых ASP .NET приложений. Кому интересны подробности этой встречи, кто хочет узнать побольше о сообществе .NET разработчиков Санкт-Петербурга и попробовать свои силы в решении задач по AppSec .NET, приглашаю под кат!

Так как на Хабре еще не писали про SPB .NET Community начну, пожалуй, с него. В июне, в Санкт-Петербурге собралось сообщество программистов, пишущих на .NET. Наша цель – это делиться опытом решения задач, с которыми мы встречаемся в ходе работы, собираться в офлайне, чтобы обсудить актуальные проблемы и новости мира .NET. Сейчас платформа переживает бум развития, тут и выход огромного количества кода в open source, и новая web платформа, и обсуждение сразу двух новых стандартов языка C#, и кроссплатформенность, которая предлагает большие возможности и грозит новым полем граблей. Как сказал Льюис, чтобы оставаться на месте, мы должны бежать. И если бежать всем вместе, то шансы не отстать повышаются (бегуны поймут метафору). Итак, что уже сделано. Мы провели первую встречу, организовали островок на IT Global Meetup, где сделали 4 доклада, смогли все познакомиться и пообщаться о планах на будущее. Судя по отзывам, доклады понравились, а идея возродить регулярные встречи .NET тусовки уже у многих была в головах.

Сейчас мы готовим вторую встречу. Она пройдет 25 июня, в 19.30 в питерском офисе компании DataArt, основной темой встречи выбрали разработку защищенных приложений. В этот четверг к нам в Санкт-Петербург приезжает известный эксперт по информационной безопасности в целом, и по платформе .NET в частности, Владимир Кочетков VladimirKochetkov. Он согласился поучаствовать в нашей встрече, так что кто знаком с Володей по блогам, вебинарам или его работе в RSDN Team, у вас есть шанс прийти и пообщаться с ним лично. В программе встречи два доклада и много общения, это «Теория Application Security .NET» Владимир Кочетков и «Практика Application Security .NET» Михаил Щербаков (мой доклад). Я с материалом по этой теме выступал на последних конференциях, это .NEXT, dotnetconf.ru, SECON. Но для митапа подготовил новые примеры и задачки, которые мы тоже разберем на встрече. А, да задачи… Не буду больше рассказывать про митап, читайте анонс в группе сообщества spbdotnet.org, регистрируйтесь по ссылке и приходите. Участие конечно бесплатное, необходима только регистрация (количество мест к сожалению, ограничено, но свободные есть).

А теперь внимание задачи.


  1. Содержит ли проблемы безопасности код следующей aspx страницы? Если содержит, то какие и в каких строках кода? Вопрос со звездочкой: какие данные нужно отправить на сервер, чтобы продемонстрировать атаки? Условия выполнения кода стандартные: на сервере IIS 8.5 с настройками по умолчанию, aspx-страница входит в web-проект с настройками по умолчанию, собирается под Framework 4.5.1.

    <%@ Page Language="C#" AutoEventWireup="true"%>
    <script language="C#" runat="server">
        protected void Page_Load(object sender, EventArgs e)
        {
            var text = TextBox1.Text + TextBox2.Text;
            if (text != String.Empty)
            {
                Label1.Text = "Input: " + text;
            }
            else
            {
                TextBox1.Text = Request["first"] + Request["second"];
            }
            
            int count;
            if (Int32.TryParse(Request["count"], out count))
            {
                for (int i = 0; i < count; i++)
                {
                    var name = String.Format("base64_item{0}", i);
                    var value = Request[name];
                    if (value != null)
                    {
                        RadioButtonList1.Items.Add(new ListItem(Encoding.UTF8.GetString(Convert.FromBase64String(value)), value));
                    }
                }
            }
        }
    </script>
     
    <html xmlns="http://www.w3.org/1999/xhtml">
    <head runat="server">
    </head>
    <body>
    <!--
        <asp:Label runat="server">
            <%= Request["first"] + Request["second"] %>
        </asp:Label>
    -->
        Preview:
        <img src="<%= ResolveUrl("~/Content/Images/" + Request["page"] + ".png")%>"/>
     
        <form id="form1" runat="server">
            <asp:Label ID="Label1" runat="server"></asp:Label><br/>
            <asp:RadioButtonList ID="RadioButtonList1" runat="server"/><br/>
            <asp:TextBox ID="TextBox1" runat="server"></asp:TextBox>
            <asp:TextBox ID="TextBox2" runat="server"></asp:TextBox><br/>
            <asp:Button ID="Button1" runat="server" Text="Save"/>
        </form>
    </body>
    </html>
    

  2. Содержит ли проблемы безопасности следующий C# код? Какими способами атакующий может проэксплуатировать уязвимости, если они есть? Как бы вы исправили этот код? Доступ к БД осуществляется через классы Entity Framework’а, CoinsDB – класс контекста нашей БД, наследник DbContext. CustomerLogin — класс нашей сущности из БД, его код есть ниже. Условия выполнения кода стандартные, как и в примере выше, БД – MS SQL.

    protected void Page_Load(object sender, EventArgs e)
    {
        using (var db = new CoinsDB())
        {
            var where = String.Empty;
            var parameters = new List<object>();
     
            var email = Request["email"];
            if (email != null)
            {
                where += String.Format(" email LIKE '{0}%'", email);
            }
     
            var field = Request["field"];
            var min = Request["min"];
            var max = Request["max"];
            if (field != null && min != null && max != null)
            {
                if (!String.IsNullOrEmpty(where))
                {
                    where += " AND";
                }
     
                where += String.Format(" {0} >= @min AND {0} <= @max", EncodeSqlField(field));
                parameters.Add(new SqlParameter("@min", min));
                parameters.Add(new SqlParameter("@max", max));
            }
     
            var query = "SELECT * FROM CustomerLogin";
            if (!String.IsNullOrEmpty(where))
            {
                query += " WHERE";
                query += where;
            }
     
            var output = db.Database.SqlQuery<CustomerLogin>(query, parameters.ToArray()).ToArray();
     
            lblOutput.Text = output.Length == 0
                ? "Not found"
                : String.Join("<br/>", output.Select(customer => customer.login + " - " + customer.rating));
        }
    }
     
    private string EncodeSqlField(string field)
    {
        return field.Replace("'", String.Empty)
            .Replace(" ", String.Empty)
            .Replace("\\", String.Empty)
            .Replace(",", String.Empty)
            .Replace("(", String.Empty)
            .Replace(")", String.Empty);
    }
    
    [Table("CustomerLogin")]
    public partial class CustomerLogin
    {
        [Key]
        [StringLength(100)]
        public string login { get; set; }
    
        [StringLength(100)]
        public string email { get; set; }
    
        public long raiting { get; set; }
        public long customerNumber { get; set; }
     
        [Required]
        [StringLength(40)]
        public string password { get; set; }
     
        public short? question_id { get; set; }
     
        [StringLength(50)]
        public string answer { get; set; }
    }
    


Ответы, пожалуйста, пишите в комментариях под спойлером. Все интересные случаи мы разберем 25 июня на митапе.
Tags:
Hubs:
+11
Comments9

Articles