Home | Data Center | Contact US | Login

Á¦¸ñ MS-SQL injections °ø°Ý ´ëóÇϱâ
÷ºÎÆÄÀÏ MS-SQL injections °ø°Ý ´ëóÇϱâ.pdf ÀÛ¼ºÀÏ 2008-09-18 12:07:56
ÀÛ¼ºÀÚ : ±â¼úÁö¿øºÎ Á¶ Å ÁØ tedcho@nextline.net

MS-SQL Database ¹é¾÷Çϱâ

ASP.NET ¹× Microsoft SQL Server°ú °°Àº °­·ÂÇÑ µ¥ÀÌÅͺ£À̽º ¼­¹öÀÇ °í±Þ ¼­¹öÃø ±â¼úÀ» ÅëÇØ °³¹ßÀÚ´Â µ¿ÀûÀÎ µ¥ÀÌÅÍ Á᫐ À¥ »çÀÌÆ®¸¦ ¸Å¿ì ½±°Ô ¸¸µé ¼ö ÀÖ½À´Ï´Ù. ÇÏÁö¸¸ ASP.NET ¹× SQLÀÇ ±â´ÉÀº SQL injections °ø°ÝÀ̶ó´Â ³Ê¹«³ª ÀϹÝÀûÀÎ °ø°Ý ¹æ½ÄÀ» ¾Ë°í ÀÖ´Â ÇØÄ¿µé¿¡°Ôµµ ½±°Ô ¾Ç¿ëµÉ ¼ö ÀÖ½À´Ï´Ù.
SQL injections °ø°Ý¿¡ ´ëÇÑ ±âº» °³³äÀº ´ÙÀ½°ú °°½À´Ï´Ù. »ç¿ëÀÚ°¡ ÅؽºÆ® »óÀÚ¿¡ ÅؽºÆ®¸¦ ÀÔ·ÂÇÒ ¼ö ÀÖµµ·Ï À¥ ÆäÀÌÁö¸¦ ¸¸µé°í ÀÌ·¯ÇÑ ÅؽºÆ®´Â µ¥ÀÌÅͺ£À̽º¿¡ ´ëÇÑ Äõ¸®¸¦ ¼öÇàÇϴµ¥ »ç¿ëµË´Ï´Ù. ÇØÄ¿´Â ÀÌ·¯ÇÑ ÅؽºÆ® »óÀÚ¿¡ Äõ¸®ÀÇ Æ¯¼ºÀ» º¯°æÇÏ¿© ¹é¿£µå µ¥ÀÌÅͺ£À̽º¿¡ ħÀÔÇϰųª µ¥ÀÌÅͺ£À̽º¸¦ ¼Õ»ó½Ãų ¼ö ÀÖ´Â À߸ø Çü¼ºµÈ SQL ¹®À» ÀÔ·ÂÇÕ´Ï´Ù.

1. SQL ¹®ÀÇ º¯È¯
¿©·¯ ASP.NET ÀÀ¿ë ÇÁ·Î±×·¥¿¡¼­´Â ¾Æ·¡¿Í °°ÀÌ Ç¥½ÃµÈ °Í°ú °°Àº ÆûÀ» »ç¿ëÇÏ¿© »ç¿ëÀÚ¸¦ ÀÎÁõÇÕ´Ï´Ù.
private void cmdLogin_Click(object sender, System.EventArgs e) {
string strCnx =
"server=localhost;database=northwind;uid=sa;pwd=;";
SqlConnection cnx = new SqlConnection(strCnx);
    cnx.Open();
    //This code is susceptible to SQL injection attacks.
string strQry = "SELECT Count(*) FROM Users WHERE UserName='" +
txtUser.Text + "' AND Password='" + txtPassword.Text + "'";
int intRecs;
    SqlCommand cmd = new SqlCommand(strQry, cnx);
intRecs = (int) cmd.ExecuteScalar();
    if (intRecs>0) {
FormsAuthentication.RedirectFromLoginPage(txtUser.Text, false);
}
else {
lblMsg.Text = "Login attempt failed.";
}
    cnx.Close();
}
Ç¥ 1

»ç¿ëÀÚ°¡ BadLogin.aspxÀÇ Login ´ÜÃ߸¦ Ŭ¸¯ÇÏ¸é »ç¿ëÀÚ°¡ ÆûÀÇ ÅؽºÆ® »óÀÚ ÄÁÆ®·Ñ¿¡ ÀÔ·ÂÇÑ °ª°ú UserName ¹× Password°¡ ÀÏÄ¡ÇÏ´Â Users Å×ÀÌºí¿¡ ÀÖ´Â ·¹ÄÚµå ¼ö¸¦ °è»êÇÏ´Â Äõ¸®¸¦ ½ÇÇàÇÏ¿© cmdLogin_Click ¸Þ¼­µå°¡ »ç¿ëÀÚ¸¦ ÀÎÁõÇϵµ·Ï ½ÃµµÇÕ´Ï´Ù.

´ëºÎºÐÀÇ °æ¿ì ÆûÀº Á¤È®È÷ ÀǵµµÈ ´ë·Î ÀÛµ¿ÇÕ´Ï´Ù. »ç¿ëÀÚ´Â Users Å×ÀÌºí¿¡ ÀÖ´Â ·¹ÄÚµå¿Í ÀÏÄ¡ÇÏ´Â »ç¿ëÀÚ À̸§ ¹× ¾ÏÈ£¸¦ ÀÔ·ÂÇÕ´Ï´Ù. µ¿ÀûÀ¸·Î »ý¼ºµÈ SQL Äõ¸®¸¦ »ç¿ëÇÏ¿© ÀÏÄ¡ÇÏ´Â ÇàÀÇ °³¼ö¸¦ °Ë»öÇÕ´Ï´Ù. ±×·± ´ÙÀ½ »ç¿ëÀÚ¸¦ ÀÎÁõÇÏ°í ¿äûµÈ ÆäÀÌÁö·Î ¸®µð·º¼ÇÇÕ´Ï´Ù. À߸øµÈ »ç¿ëÀÚ À̸§ ¹× ¾ÏÈ£¸¦ ÀÔ·ÂÇÏ´Â »ç¿ëÀÚ´Â ÀÎÁõµÇÁö ¾Ê½À´Ï´Ù. ÇÏÁö¸¸ ÀÌ °æ¿ì¿¡µµ ÇØÄ¿°¡ UserName ÅؽºÆ® »óÀÚ¿¡ °Ñº¸±â¿¡´Â À߸øµÈ °ÍÀÌ ¾ø´Â ´ÙÀ½°ú °°Àº ÅؽºÆ®¸¦ ÀÔ·ÂÇÏ¿© À¯È¿ÇÑ »ç¿ëÀÚ À̸§ ¹× ¾ÏÈ£¸¦ ¾ËÁö ¸øÇÏ´õ¶ó°í ½Ã½ºÅÛ¿¡ ħÀÔÇÒ ¼ö ÀÖ½À´Ï´Ù. ¡®Or 1=1 --ÇØÄ¿´Â À߸ø Çü¼ºµÈ SQLÀ» Äõ¸®¿¡ ÁÖÀÔÇÏ¿© ½Ã½ºÅÛ¿¡ ħÀÔÇÕ´Ï´Ù. ÀÌ °æ¿ìÀÇ ÇØÅ·Àº ´ÙÀ½°ú °°ÀÌ »ç¿ëÀÚ°¡ ÀÔ·ÂÇÑ °íÁ¤ ¹®ÀÚ¿­ ¹× °ªÀÇ ¿¬°áÀ» ÅëÇØ ½ÇÇà Äõ¸®°¡ Çü¼ºµÇ±â ¶§¹®¿¡ ÀÛµ¿µË´Ï´Ù.

String strQry = ¡°SELECT Count(*) FROM Users WHERE USerName=¡¯¡±+ txtUser.Text + ¡±¡¯ AND PassWord=¡¯¡± + txtPassword.Text + ¡°¡¯¡±; À¯È¿ÇÑ »ç¿ëÀÚ À̸§ÀÎ ¡°Paul¡±°ú ¾ÏÈ£ ¡°password¡±¸¦ »ç¿ëÀÚ°¡ ÀÔ·ÂÇÏ´Â °æ¿ì strQry´Â ´ÙÀ½°ú °°ÀÌ µË´Ï´Ù. SELECT Count(*) FROM Users WHERE UserName=¡¯Paul¡¯ AND Password=¡¯password¡¯ ÇÏÁö¸¸ ÇØÄ¿°¡ ´ÙÀ½À» ÀÔ·ÂÇÏ¸é ¡® Or 1=1 – Äõ¸®°¡ ´ÙÀ½°ú °°ÀÌ µÇ´Ï´Ù. SELECT Cont(*) FROM Users WHERE UserName=¡±Or 1=1 –¡® AND Password=¡±

ÀÌÁß ÇÏÀÌÇÂÀº SQL ¿¡¼­ ÁÖ¼®ÀÇ ½ÃÀÛ ºÎºÐÀ» ³ªÅ¸³»¹Ç·Î Äõ¸®´Â ´ÙÀ½°ú °°ÀÌ µË´Ï´Ù.
SELECT Count (*) FROM Users WHERE UserName=¡± Or 1=1 ½Ä 1=1Àº Å×À̺íÀÇ ¸ðµç Çà¿¡ ´ëÇØ Ç×»ó TrueÀÌ°í ´Ù¸¥ ½ÄÀÌ Æ÷ÇÔµÈ True ½Ä or¡¯d´Â Ç×»ó 0 ÀÌ ¾Æ´Ô ·¹ÄÚµå °³¼ö¸¦ ¹ÝȯÇÕ´Ï´Ù.
ÀϺΠSQL injections °ø°Ý¿¡´Â Æû ÀÎÁõÀÌ Æ÷ÇÔµÇÁö ¾Ê½À´Ï´Ù. Æû ÀÎÁõ°ú °ü·ÃÇÑ SQL injections °ø°Ý¿¡ ÇÊ¿äÇÑ »çÇ×Àº µ¿ÀûÀ¸·Î ±¸¼ºµÈ ÀϺΠSQL°ú Æ®·¯½ºÆ®µÇÁö ¾ÊÀº »ç¿ëÀÚ ÀÔ·ÂÀÌ ÀÖ´Â ÀÀ¿ë ÇÁ·Î±×·¥ÀÔ´Ï´Ù. Á¤È®ÇÑ Á¶°Ç¸¸ ÁÖ¾îÁø´Ù¸é ÀÌ·¯ÇÑ °ø°ÝÀ¸·Î ÀÎÇÑ ÇÇÇØ ¹üÀ§¸¦ ÇØÄ¿ÀÇ SQL ¾ð¾î ¹× µ¥ÀÌÅͺ£À̽º ±¸¼º¿¡ ´ëÇÑ Áö½Ä ¼öÁØÀ¸·Î¸¸ Á¦ÇÑÇÒ ¼ö ÀÖ½À´Ï´Ù.

ÀÌÁ¦ badProductList.aspx¿¡¼­ °¡Á®¿Â¾Æ·¡ ¡° Ç¥2 ¡°¿¡ Ç¥½ÃµÈ Äڵ带 »ìÆ캸½Ã¸é, ÀÌ ÆäÀÌÁö´Â Northwind µ¥ÀÌÅͺ£À̽ºÀÇ Á¦Ç°À» Ç¥½ÃÇÏ°í »ç¿ëÀÚ°¡ txtFilter¶ó´Â ÅؽºÆ® »óÀÚ¸¦ »ç¿ëÇÏ¿© Á¦Ç° °á°ú¸ñ·ÏÀ» ÇÊÅ͸µÇϵµ·Ï ÇÒ ¼ö ÀÖ½À´Ï´Ù. ¸¶Áö¸· ¿¹¿¡¼­¿Í °°ÀÌ ÀÌ ÆäÀÌÁö´Â ½ÇÇà SQLÀÌ »ç¿ëÀÚ°¡ ÀÔ·ÂÇÏ´Â °ªÀ¸·Î µ¿ÀûÀ¸·Î »ý¼ºµÇ±â ¶§¹®¿¡ SQL injections °ø°Ý¿¡ ´çÇÒ °¡´É¼ºÀÌ ³ô½À´Ï´Ù. ÀÌ·¯ÇÑ Æ¯Á¤ ÆäÀÌÁö´Â ¾à»èºü¸¥ ÇØÄ¿°¡ °ø°ÝÇÏ¿© ±â¹Ð Á¤º¸¸¦ ÈÉÄ¡°í, µ¥ÀÌÅͺ£À̽ºÀÇ µ¥ÀÌÅ͸¦ º¯°æÇÏ°í, µ¥ÀÌÅͺ£À̽º ·¹Äڵ带 ¼Õ»ó½ÃÅ°°í, ½ÉÁö¾î´Â »õ·Î¿î µ¥ÀÌÅͺ£À̽º »ç¿ëÀÚ °èÁ¤À» ¸¸µé ¼öµµ Àֱ⠶§¹®¿¡ ÇØÄ¿¿¡°Ô´Â õ±¹°úµµ °°½À´Ï´Ù.

SQL Server¸¦ Æ÷ÇÔÇÑ ´ëºÎºÐÀÇ SQL ȣȯ µ¥ÀÌÅͺ£À̽º´Â ¸ÞŸµ¥ÀÌÅ͸¦ sysobjects, syscolumns, sysindexes µîÀÇ À̸§À¸·Î ÀÏ·ÃÀÇ ½Ã½ºÅÛ Å×ÀÌºí¿¡ ÀúÀåÇÕ´Ï´Ù. Áï, ÇØÄ¿´Â ÀÌ·¯ÇÑ ½Ã½ºÅÛ Å×À̺íÀ» »ç¿ëÇÏ¿© µ¥ÀÌÅͺ£À̽º¿¡ ´ëÇÑ ½ºÅ°¸¶ Á¤º¸¸¦ È®½ÅÇÏ°í Ãß°¡ÀûÀÎ µ¥ÀÌÅͺ£À̽º ¼Õ»óÀ» À§ÇÑ µµ¿òÀ» ¾òÀ» ¼ö ÀÖ½À´Ï´Ù. ¿¹¸¦ µé¾î ´ÙÀ½°ú °°ÀÌ txtFilter ÅؽºÆ® »óÀÚ¿¡ ÀÔ·ÂµÈ ÅؽºÆ®´Â µ¥ÀÌÅͺ£À̽º¿¡¼­ »ç¿ëÀÚ Å×À̺íÀÇ À̸§À» È®ÀÎÇÏ´Â µ¥ »ç¿ëµÉ ¼ö ÀÖ½À´Ï´Ù.
' UNION SELECT id, name, '', 0 FROM sysobjects WHERE xtype ='U' --
private void cmdFilter_Click(object sender, System.EventArgs e) {
dgrProducts.CurrentPageIndex = 0;
bindDataGrid();
}
private void bindDataGrid() {
dgrProducts.DataSource = createDataView();
dgrProducts.DataBind();
}
private DataView createDataView()  {
string strCnx =
"server=localhost;uid=sa;pwd=;database=northwind;";
string strSQL = "SELECT ProductId, ProductName, " +
"QuantityPerUnit, UnitPrice FROM Products";
    //This code is susceptible to SQL injection attacks.
if (txtFilter.Text.Length > 0) {
strSQL += " WHERE ProductName LIKE '" + txtFilter.Text + "'";
}
    SqlConnection cnx  = new SqlConnection(strCnx);
SqlDataAdapter sda = new SqlDataAdapter(strSQL, cnx);
DataTable dtProducts = new DataTable();
sda.Fill(dtProducts);
    return dtProducts.DefaultView;
}
Ç¥ 2

UNION ¹®Àº ÇØÄ¿°¡ ÇÑ Äõ¸®ÀÇ °á°ú¸¦ ´Ù¸¥ Äõ¸®·Î ºÐÇÒÇÒ ¼ö ÀÖµµ·Ï Çϱ⠶§¹®¿¡ ÇØÄ¿¿¡°Ô ƯÈ÷ À¯¿ëÇÕ´Ï´Ù. ÀÌ·¯ÇÑ °æ¿ì ÇØÄ¿´Â µ¥ÀÌÅͺ£À̽ºÀÇ »ç¿ëÀÚ Å×À̺í À̸§À» Á¦Ç° Å×À̺íÀÇ ¿ø·¡ Äõ¸®·Î ºÐÇÒÇÕ´Ï´Ù. ¿©±â¿¡ »ç¿ëµÈ ¹æ¹ýÀº ´ÜÁö ¿­ÀÇ °³¼ö¿Í µ¥ÀÌÅÍ Çü½ÄÀ» ¿ø·¡ÀÇ Äõ¸®¿Í ÀÏÄ¡½ÃÅ°´Â °Í »ÓÀÔ´Ï´Ù. ÀÌÀü Äõ¸®´Â Users¶ó´Â Å×À̺íÀÌ µ¥ÀÌÅͺ£À̽º¿¡ ÀÖÀ½À» ³ªÅ¸³¾ ¼ö ÀÖ½À´Ï´Ù. µÎ ¹ø° Äõ¸®´Â Users Å×ÀÌºí¿¡ ÀÖ´Â ¿­À» ³ëÃâ½Ãų ¼ö ÀÖ½À´Ï´Ù. ÇØÄ¿´Â ÀÌ·¯ÇÑ Á¤º¸¸¦ »ç¿ëÇÏ¿© txtFilter ÅؽºÆ® »óÀÚ¿¡ ´ÙÀ½À» ÀÔ·ÂÇÒ ¼ö ÀÖ½À´Ï´Ù. ' UNION SELECT 0, UserName, Password, 0 FROM Users -- ÀÌ Äõ¸®¸¦ ÀÔ·ÂÇÏ¸é ¾Æ·¡±×¸² 1°ú °°ÀÌ Users Å×ÀÌºí¿¡ ÀÖ´Â »ç¿ëÀÚ À̸§ ¹× ¾ÏÈ£¸¦ ³ëÃâ½Ãŵ´Ï´Ù.

±×¸² 1

SQL injections °ø°ÝÀº ¶ÇÇÑ µ¥ÀÌÅ͸¦ º¯°æÇϰųª µ¥ÀÌÅͺ£À̽º¸¦ ¼Õ»ó½ÃÅ°´Â µ¥¿¡µµ »ç¿ëµÉ ¼ö ÀÖ½À´Ï´Ù. SQL injections ÇØÄ¿´Â txtFilter ÅؽºÆ® »óÀÚ¿¡ ´ÙÀ½À» ÀÔ·ÂÇÏ¿© ù ¹ø° Á¦Ç°ÀÇ °¡°ÝÀ» $18¿¡¼­ $0.01·Î ¹Ù²Ù°í ÀÌ·¯ÇÑ »ç½ÇÀ» ´Ù¸¥ »ç¶÷ÀÌ ´«Ä¡Ã¤±â Àü¿¡ ÀϺΠÁ¦Ç°À» Àçºü¸£°Ô ±¸¸ÅÇÒ ¼ö ÀÖ½À´Ï´Ù. '; UPDATE Products SET UnitPrice = 0.01 WHERE ProductId = 1--

ÀÌ·¯ÇÑ ÇØÅ·Àº SQL Server¿¡¼­ ¼¼¹ÌÄÝ·ÐÀ̳ª °ø¹éÀ» »ç¿ëÇÏ¿© ±¸ºÐµÈ ¿©·¯ SQL ¹®À» ÇÔ²² ÀÔ·ÂÇÒ ¼ö ÀÖµµ·Ï Çã¿ëÇϱ⠶§¹®¿¡ °¡´ÉÇÕ´Ï´Ù. ÀÌ ¿¹¿¡¼­ DataGrid´Â ¾Æ¹« °Íµµ Ç¥½ÃÇÏÁö ¾ÊÁö¸¸ ¾÷µ¥ÀÌÆ® Äõ¸®´Â ¼º°øÀûÀ¸·Î ½ÇÇàµË´Ï´Ù. ÀÌ·¯ÇÑ °°Àº ±â¼úÀ» »ç¿ëÇϸé DROP TABLE ¹®À» ½ÇÇàÇϰųª »õ·Î¿î »ç¿ëÀÚ °èÁ¤À» ¸¸µé°í ÀÌ »ç¿ëÀÚ¸¦ sysadmin ¿ªÇÒ¿¡ Ãß°¡ÇÏ´Â ½Ã½ºÅÛ ÀúÀå ÇÁ·Î½ÃÀú¸¦ ½ÇÇàÇÒ ¼öµµ ÀÖ½À´Ï´Ù. ÀÌ·¯ÇÑ ÇØÅ·Àº ¸ðµÎ ¡°Ç¥ 2¡±¿¡ Ç¥½ÃµÈ BadProductList.aspx ÆäÀÌÁö¸¦ »ç¿ëÇÏ¿© °¡´ÉÇÕ´Ï´Ù.

2. µ¿ÀÏÇÑ ÇØÅ· ±âȸ
SQL injections °ø°ÝÀº SQL Server¿¡¸¸ ±¹ÇÑµÈ ¹®Á¦°¡ ¾Æ´Õ´Ï´Ù. Oracle, MySQL, DB2, Sybase µîÀÇ ´Ù¸¥µ¥ÀÌÅͺ£À̽º¿¡¼­µµ ÀÌ·¯ÇÑ Á¾·ùÀÇ °ø°ÝÀ» ¹ÞÀ» ¼ö ÀÖ½À´Ï´Ù. SQL injections °ø°ÝÀº SQL ¾ð¾î¿¡ ´ÙÀ½°ú °°ÀÌ °­·ÂÇÏ°í À¯¿¬ÇÑ ¿©·¯ ±â´ÉÀÌ Æ÷ÇԵǾî Àֱ⠶§¹®¿¡ °¡´ÉÇÕ´Ï´Ù.

• ÀÌÁß ÇÏÀÌÇÂÀ» »ç¿ëÇÏ¿© SQL ¹®¿¡ ÁÖ¼®À» Æ÷ÇÔ½Ãų ¼ö ÀÖ´Â ±â´É
• ¿©·¯ SQL ¹®À» ÇÔ²² ÀÔ·ÂÇÏ°í À̸¦ ÀÏ°ý 󸮷Π½ÇÇàÇÒ ¼ö ÀÖ´Â ±â´É
• SQLÀ» »ç¿ëÇÏ¿© Ç¥ÁØ ½Ã½ºÅÛ Å×À̺í ÁýÇÕÀ¸·ÎºÎÅÍ ¸ÞŸµ¥ÀÌÅ͸¦ Äõ¸®ÇÒ ¼ö ÀÖ´Â ±â´É

ÀϹÝÀûÀ¸·Î µ¥ÀÌÅͺ£À̽º¿¡¼­ Áö¿øµÇ´Â SQL ¾ð¾îÀÇ ±â´ÉÀÌ °­·ÂÇÒ¼ö·Ï µ¥ÀÌÅͺ£À̽º¿¡ ´ëÇÑ °ø°Ý °¡´É¼º
µµ ³ô¾ÆÁý´Ï´Ù. µû¶ó¼­ SQL Server°¡ injections °ø°ÝÀÇ ÀϹÝÀûÀÎ ´ë»óÀÌ µÇ´Â °ÍÀÔ´Ï´Ù.

SQL injections °ø°ÝÀº ASP.NET ÀÀ¿ë ÇÁ·Î±×·¥À¸·Î¸¸ Á¦ÇѵÇÁö ¾Ê½À´Ï´Ù. ±âÁ¸ÀÇ ASP, Java, JSP ¹× PHP ÀÀ¿ë ÇÁ·Î±×·¥µµ ¸ðµÎ °°Àº À§ÇèÀÌ ÀÖ½À´Ï´Ù. ½ÇÁ¦·Î SQL injections °ø°ÝÀº µ¥½ºÅ©Åé ÀÀ¿ë ÇÁ·Î±×·¥¿¡ ´ëÇؼ­µµ ¼öÇàµÉ ¼ö ÀÖ½À´Ï´Ù. ¿¹¸¦ µé¾î ÀÌ ¹®¼­¿¡ ´ëÇÑ ´Ù¿î·Îµå ÆÄÀÏ(ÀÌ ¹®¼­ÀÇ ¸Ç À§¿¡ ÀÖ´Â ¸µÅ©·Î Á¦°ø)¿¡ SQL injections °ø°ÝÀ» ¹ÞÀ» ¼ö ÀÖ´Â SQLInjectWinFormÀ̶ó´Â Windows Forms ÀÀ¿ë ÇÁ·Î±×·¥ ¿¹Á¦¸¦ Æ÷ÇԵǾî ÀÖ½À´Ï´Ù.

SQL injections °ø°Ý ¹æÁö¸¦ À§ÇÑ ÇÑ µÎ °³ÀÇ ÇÙ½É ¹æ¹ýÀ» ½±°Ô ¼³¸íÇÒ ¼öµµ ÀÖÁö¸¸ ÀÌ ¹®Á¦¿¡ ´ëÇؼ­´Â °èÃþÀû ¹æ½ÄÀ» »ç¿ëÇÏ´Â °ÍÀÌ °¡Àå ÁÁ½À´Ï´Ù. ÀÌ·¯ÇÑ ¹æ½Ä¿¡¼­´Â ÀϺΠÃë¾à¼ºÀ¸·Î ÀÎÇØ º¸¾È ¹æ½Ä Áß Çϳª°¡ ¹«È¿È­µÇ´õ¶óµµ °è¼ÓÇؼ­ º¸È£ »óŸ¦ À¯ÁöÇÒ ¼ö ÀÖ½À´Ï´Ù. ±ÇÀåµÇ´Â °èÃþÀº ¾Æ·¡ ±×¸²°ú °°½À´Ï´Ù.

±×¸² 2

3. ¸ðµç ÀԷ¿¡ ´ëÇÑ °Ë»ç ¼öÇà
À§ ±×¸²¿¡ ³ª¿­µÈ ù ¹ø° ¿øÄ¢Àº ¸Å¿ì Áß¿äÇÑ °ÍÀÔ´Ï´Ù. ¸ðµç »ç¿ëÀÚ ÀÔ·ÂÀº ¾ÇÀÇÀûÀÎ °ÍÀ¸·Î °£ÁÖÇϽʽÿÀ! µ¥ÀÌÅͺ£À̽º Äõ¸®¿¡¼­ °Ë»çµÇÁö ¾ÊÀº »ç¿ëÀÚ ÀÔ·ÂÀ» »ç¿ëÇؼ­´Â ¾ÈµË´Ï´Ù.

ƯÈ÷ RegularExpressionValidator ÄÁÆ®·Ñ°ú °°Àº ASP.NET À¯È¿¼º °Ë»ç ÄÁÆ®·ÑÀº »ç¿ëÀÚ ÀÔ·ÂÀÇ À¯È¿¼ºÀ» °Ë»çÇϱâ À§ÇÑ ÈǸ¢ÇÑ µµ±¸ÀÔ´Ï´Ù.

À¯È¿¼º °Ë»ç¿¡ ´ëÇÑ ±âº»ÀûÀÎ µÎ °¡Áö ¹æ½ÄÀº ¹®Á¦°¡ ÀÖ´Â ¹®ÀÚ¸¦ Çã¿ëÇÏÁö ¾Ê°Å³ª ÀûÀº ¼öÀÇ Çʼö ¹®ÀÚ¸¸ Çã¿ëÇÏ´Â °ÍÀÔ´Ï´Ù. ÇÏÀÌÇ°ú ÀÛÀºµû¿ÈÇ¥¿Í °°Àº ¹®Á¦°¡ µÇ´Â ÀϺΠ¹®ÀÚ¸¦ ½±°Ô Çã¿ëÇÏÁö ¾ÊÀ» ¼öµµ ÀÖÁö¸¸ ÀÌ ¹æ¹ýÀº µÎ °¡Áö ÀÌÀ¯·Î ÀÎÇØ ÀûÇÕÇÏÁö ¾ÊÀ» ¼ö ÀÖ½À´Ï´Ù. ù ¹ø°, ÇØÄ¿¿¡°Ô À¯¿ëÇÏ°Ô »ç¿ëµÇ´Â ¹®ÀÚ¸¦ ³õÄ¥ ¼ö ÀÖÀ¸¸ç, µÎ ¹ø° À߸øµÈ ¹®ÀÚ¸¦ Ç¥ÇöÇÏ´Â ¹æ¹ýÀÌ ¿©·¯ °¡ÁöÀÏ ¼ö ÀÖ½À´Ï´Ù. ¿¹¸¦ µé¾î ÇØÄ¿´Â ÀÛÀºµû¿ÈÇ¥¸¦ À̽ºÄÉÀÌÇÁ ó¸®ÇÏ¿© À¯È¿¼º °Ë»ç Äڵ忡¼­ ³õÄ¡µµ·Ï ¸¸µé°Å³ª À̽ºÄÉÀÌÇÁ ó¸®µÈ µû¿ÈÇ¥¸¦ µ¥ÀÌÅͺ£À̽º¿¡ Àü´ÞÇÏ¿© ÀϹÝÀûÀÎ ÀÛÀºµû¿ÈÇ¥ ¹®ÀÚ¿Í µ¿ÀÏÇÏ°Ô Ãë±ÞµÇµµ·Ï ÇÒ ¼ö ÀÖ½À´Ï´Ù. ´õ ³ªÀº ¹æ¹ýÀº Çã¿ë °¡´ÉÇÑ ¹®ÀÚ¸¦ ½Äº°ÇÏ°í ÇØ´ç ¹®ÀÚ¸¸ Çã¿ëÇÏ´Â °ÍÀÔ´Ï´Ù. ÀÌ·¯ÇÑ ¹æ½Ä¿¡´Â ´õ ¸¹Àº ÀÛ¾÷ÀÌ ÇÊ¿äÇÏÁö¸¸ ÀԷ¿¡ ´ëÇØ º¸´Ù ¼¼¹ÐÇÑ Á¦¾î°¡ °¡´ÉÇÏ¸ç º¸´Ù ¾ÈÀüÇÕ´Ï´Ù. ¾î¶² ¹æ½ÄÀ» »ç¿ëÇÏ´ø °£¿¡ ÀϺΠÇØÅ·¿¡´Â ¸¹Àº ¼öÀÇ ¹®ÀÚ°¡ ÇÊ¿äÇϹǷΠÀԷ¿¡ ´ëÇÑ ±æÀ̸¦ Á¦ÇÑÇÒ ¼ö ÀÖ½À´Ï´Ù.

GoodLogin.aspx(´Ù¿î·Îµå Äڵ忡¼­ Á¦°ø)¿¡´Â µÎ °³ÀÇ ÀÏ¹Ý ½Ä À¯È¿¼º °Ë»ç ÄÁÆ®·ÑÀÌ Æ÷ÇԵǸç, ÀÌ Áß¿¡¼­ Çϳª´Â »ç¿ëÀÚ À̸§¿¡ ´ëÇÑ ÄÁÆ®·ÑÀÌ°í ´Ù¸¥ Çϳª´Â ¾ÏÈ£¿¡ ´ëÇÑ ÄÁÆ®·ÑÀÔ´Ï´Ù. ¶ÇÇÑ ¿©±â¿¡´Â 4-12°³ÀÇ ¼ýÀÚ, ¾ËÆĺª ¹®ÀÚ ¹× ¹ØÁÙ·Î ÀÔ·ÂÀ» Á¦ÇÑÇÏ´Â ´ÙÀ½°ú °°Àº ValidationExpression °ªÀÌ Æ÷ÇԵǾî ÀÖ½À´Ï´Ù. [\d_a-zA-Z]{4,12}

»ç¿ëÀÚ°¡ ÅؽºÆ® »óÀÚ¿¡ ÀáÀçÀûÀ¸·Î ¼Õ»óµÉ °¡´É¼ºÀÌ ÀÖ´Â ¹®ÀÚ¸¦ ÀÔ·ÂÇϵµ·Ï Çã¿ëÇØ¾ß ÇÒ ¼ö ÀÖ½À´Ï´Ù. ¿¹¸¦ µé¾î »ç¿ëÀÚ À̸§ÀÇ ÀϺηΠÀÛÀºµû¿ÈÇ¥(¶Ç´Â ¾îÆ÷½ºÆ®·ÎÇÇ)¸¦ ÀÔ·ÂÇØ¾ß ÇÒ ¼ö ÀÖ½À´Ï´Ù. ÀÌ·¯ÇÑ °æ¿ì Á¤±Ô ½ÄÀ̳ª String.Replace ¸Þ¼­µå¸¦ »ç¿ëÇÏ¿© °¢°¢ÀÇ ÀÛÀºµû¿ÈÇ¥¸¦ µÎ °³ÀÇ ÀÛÀºµû¿ÈÇ¥·Î ¹Ù²Ù¸é ÀÛÀºµû¿ÈÇ¥¸¦ ¾ÈÀüÇÏ°Ô ·»´õ¸µÇÒ ¼ö ÀÖ½À´Ï´Ù. ¿¹¸¦ µé¸é ´ÙÀ½°ú °°½À´Ï´Ù. string strSanitizedInput = strInput.Replace("'", "''");

4. µ¿Àû SQL ¹æÁö
ÀÌ ¹®¼­¿¡¼­ ¼³¸íÇÏ´Â SQL injections °ø°ÝÀº ¸ðµÎ µ¿Àû SQLÀÇ ½ÇÇàÀ» ±â¹ÝÀ¸·Î ÇÕ´Ï´Ù. Áï, »ç¿ëÀÚ°¡ ÀÔ·ÂÇÑ °ª°ú SQLÀ» ¿¬°áÇÏ¿© »ý¼ºµÇ´Â SQL ¹®ÀÔ´Ï´Ù. ÇÏÁö¸¸ ¸Å°³ º¯¼ö°¡ ÀÖ´Â SQLÀ» »ç¿ëÇϸé ÇØÄ¿°¡ SQLÀ» Äڵ忡 ÁÖÀÔÇÒ ¼ö ÀÖ´Â °¡´É¼ºÀÌ Å©°Ô ÁÙ¾îµì´Ï´Ù.

private void cmdLogin_Click(object sender, System.EventArgs e) {
string strCnx = ConfigurationSettings.AppSettings["cnxNWindBad"];
using (SqlConnection cnx = new SqlConnection(strCnx))
{
SqlParameter prm;
cnx.Open();
string strQry =
"SELECT Count(*) FROM Users WHERE UserName=@username " +
"AND Password=@password";
int intRecs;
SqlCommand cmd = new SqlCommand(strQry, cnx);
cmd.CommandType= CommandType.Text;
prm = new SqlParameter("@username",SqlDbType.VarChar,50);
prm.Direction=ParameterDirection.Input;
prm.Value = txtUser.Text;
cmd.Parameters.Add(prm);
prm = new SqlParameter("@password",SqlDbType.VarChar,50);
prm.Direction=ParameterDirection.Input;
prm.Value = txtPassword.Text;
cmd.Parameters.Add(prm);           
intRecs = (int) cmd.ExecuteScalar();
if (intRecs>0) {
FormsAuthentication.RedirectFromLoginPage(txtUser.Text, false);
}
else {
lblMsg.Text = "Login attempt failed.";
}
}
}
Ç¥ 3
  
À§ÀÇ Ç¥3ÀÇ ÄÚµå´Â ¸Å°³ º¯¼ö°¡ ÀÖ´Â SQLÀ» »ç¿ëÇÏ¿© injections °ø°ÝÀ» ¹æÁöÇÕ´Ï´Ù. ¸Å°³ º¯¼ö°¡ ÀÖ´Â SQLÀº »ç¿ëÀÚ°¡ Àӽà SQLÀ» »ç¿ëÇØ¾ß ÇÏ´Â °æ¿ì ¶Ù¾î³­ ¼º´ÉÀ» º¸¿© ÁÝ´Ï´Ù. ÀÌ·¯ÇÑ ¹æ½ÄÀº IT ºÎ¼­¿¡¼­ ÀúÀå ÇÁ·Î½ÃÀú¸¦ ¹ÏÁö ¾Ê°Å³ª ¹öÀü 5.0±îÁö À̸¦ Áö¿øÇÏÁö ¾ÊÀº MySQL°ú °°Àº Á¦Ç°À» »ç¿ëÇÏ´Â °æ¿ì¿¡ ÇʼöÀûÀÔ´Ï´Ù. ÇÏÁö¸¸ °¡´ÉÇÏ´Ù¸é Ãß°¡ ±â´É¿¡ ´ëÇØ ÀúÀå ÇÁ·Î½ÃÀú¸¦ »ç¿ëÇÏ¿© µ¥ÀÌÅͺ£À̽º¿¡ ÀÖ´Â ±âº» Å×ÀÌºí¿¡ ´ëÇÑ ¸ðµç ±ÇÇÑÀ» Á¦°ÅÇÏ¿© ±×¸² 1¿¡ Ç¥½ÃµÈ °Í°ú °°Àº Äõ¸®¸¦ ¸¸µé ¼ö ÀÖ´Â °¡´É¼ºÀ» Á¦°ÅÇØ¾ß ÇÕ´Ï´Ù.

private void cmdLogin_Click(object sender, System.EventArgs e) {
string strCnx =
ConfigurationSettings.AppSettings["cnxNWindBetter"];
using (SqlConnection cnx = new SqlConnection(strCnx))
{
SqlParameter prm;
        cnx.Open();
        string strAccessLevel;
        SqlCommand cmd = new SqlCommand("procVerifyUser", cnx);
cmd.CommandType= CommandType.StoredProcedure;
        prm = new SqlParameter("@username",SqlDbType.VarChar,50);
prm.Direction=ParameterDirection.Input;
prm.Value = txtUser.Text;
cmd.Parameters.Add(prm);
        prm = new SqlParameter("@password",SqlDbType.VarChar,50);
prm.Direction=ParameterDirection.Input;
prm.Value = txtPassword.Text;
cmd.Parameters.Add(prm);           
        strAccessLevel = (string) cmd.ExecuteScalar();
        if (strAccessLevel.Length>0) {
FormsAuthentication.RedirectFromLoginPage(txtUser.Text, false);
}
else {
lblMsg.Text = "Login attempt failed.";
}
}
}
Ç¥ 4


Ç¥ 4¿¡ Ç¥½ÃµÈ BetterLogin.aspx´Â procVerifyUser¶ó´Â ÀúÀå ÇÁ·Î½ÃÀú¸¦ »ç¿ëÇÏ¿© »ç¿ëÀÚ¿¡ ´ëÇÑ À¯È¿¼ºÀ» °Ë»çÇÕ´Ï´Ù.

5. ÃÖ¼Ò ±ÇÇÑÀ¸·Î ½ÇÇà
BadLogin.aspx ¹× BadProductList.aspx¿¡¼­ º¸¿©Áø À߸øµÈ ±¸Çö ¹æ¹ý Áß Çϳª´Â sa °èÁ¤À» ÅëÇØ ¿¬°á ¹®ÀÚ¿­À» »ç¿ëÇÑ´Ù´Â Á¡ÀÔ´Ï´Ù. ´ÙÀ½Àº Web.config¿¡¼­ ¹ß°ßÇÒ ¼ö ÀÖ´Â ¿¬°á ¹®ÀÚ¿­ÀÔ´Ï´Ù.
<add key="cnxNWindBad" value="server=localhost;uid=sa;pwd=;database=northwind;" />

ÀÌ °èÁ¤Àº ·Î±×ÀÎ »ý¼º°ú µ¥ÀÌÅͺ£À̽º »èÁ¦ µî °ÅÀÇ ¸ðµç ÀÛ¾÷À» ¼öÇàÇÒ ¼ö ÀÖ´Â System Administrators ¿ªÇÒ·Î ½ÇÇàµË´Ï´Ù. ¸»ÇÒ ÇÊ¿äµµ ¾øÀÌ ÀÀ¿ë ÇÁ·Î±×·¥ µ¥ÀÌÅͺ£À̽º ¾×¼¼½º¿¡ ´ëÇØ sa(¶Ç´Â °í±Þ ±ÇÇÑÀÌ ÀÖ´Â °èÁ¤)¸¦ »ç¿ëÇÏ´Â °ÍÀº ¸Å¿ì À߸øµÈ »ý°¢ÀÔ´Ï´Ù. ´ë½Å Á¦ÇÑµÈ ¾×¼¼½º °èÁ¤À» ¸¸µé°í À̸¦ »ç¿ëÇϵµ·Ï ÇÏ´Â °ÍÀÌ ÈξÀ ÁÁ½À´Ï´Ù. GoodLogin.aspx¿¡ »ç¿ëµÈ °èÁ¤Àº ´ÙÀ½°ú °°Àº ¿¬°á ¹®ÀÚ¿­À» »ç¿ëÇÕ´Ï´Ù.
<add key="cnxNWindGood" value="server=localhost;uid=NWindReader;pwd=utbbeesozg4d; database=northwind;" />
NWindReader °èÁ¤Àº db_datareader ¿ªÇÒ¿¡ µû¶ó ½ÇÇàµÇ¸ç ÀÌ ¿ªÇÒÀº µ¥ÀÌÅͺ£À̽º¿¡ ´ëÇÑ Å×À̺íÀÇ Àбâ·Î ¾×¼¼½º¸¦ Á¦ÇÑÇÕ´Ï´Ù. BetterLogin.aspx´Â ÀúÀå ÇÁ·Î½ÃÀú¿Í WebLimitedUser ·Î±×ÀÎÀ» »ç¿ëÇÏ¿© »óȲÀ» ´õ¿í Çâ»ó½ÃÄÑ ÁÝ´Ï´Ù. ÀÌ ·Î±×Àο¡´Â ÇØ´ç ÀúÀå ÇÁ·Î½ÃÀú¸¦ ½ÇÇàÇÏ´Â ±ÇÇѸ¸ Æ÷ÇԵǾî ÀÖÀ¸¸ç ±âº» Å×ÀÌºí¿¡ ´ëÇؼ­´Â ¾î¶°ÇÑ ±ÇÇѵµ ¾ø½À´Ï´Ù.

6. ±â¹Ð Á¤º¸¸¦ ¾ÈÀüÇÏ°Ô ÀúÀåÇϱâ
±×¸² 1¿¡ Ç¥½ÃµÈ SQL injections °ø°ÝÀº Users Å×À̺íÀÇ »ç¿ëÀÚ À̸§°ú ¾ÏÈ£¸¦ ³ëÃâ½Ãŵ´Ï´Ù. ÀÌ·¯ÇÑ Á¾·ùÀÇ Å×À̺íÀº ÀϹÝÀûÀ¸·Î Æû ÀÎÁõÀ» Àû¿ëÇÏ´Â °æ¿ì¿¡ »ç¿ëµÇ¸ç ´ëºÎºÐÀÇ ÀÀ¿ë ÇÁ·Î±×·¥¿¡¼­ ¾ÏÈ£´Â ÀÏ¹Ý ÅؽºÆ®·Î ÀúÀåµË´Ï´Ù. ´õ ³ªÀº ¹æ¹ýÀº µ¥ÀÌÅͺ£À̽º¿¡¼­ ¾ÏȣȭµÈ ¾ÏÈ£ ¶Ç´Â ÇØ½ÃµÈ ¾ÏÈ£¸¦ ÀúÀåÇÏ´Â °ÍÀÔ´Ï´Ù. ÇØ½ÃµÈ ¾ÏÈ£´Â ¾ÏÈ£¸¦ Çص¶ÇÒ ¼ö ¾ø±â ¶§¹®¿¡ ¾ÏȣȭµÈ ¾ÏÈ£º¸´Ù ¾ÈÀüÇÕ´Ï´Ù. Çؽÿ¡ salt(¾Ïȣȭ ¹æ½ÄÀ¸·Î ¾ÈÀüÇÑ ÀÓÀÇ °ª)¸¦ Ãß°¡ÇÏ¿© ÇØ½ÃµÈ ¾ÏÈ£ÀÇ º¸¾È ¼º´ÉÀ» ´õ¿í ³ôÀÏ ¼öµµ ÀÖ½À´Ï´Ù. BestLogin.aspx¿¡´Â »ç¿ëÀÚ°¡ ÀÔ·ÂÇÑ ¾ÏÈ£¸¦ SecureUsers Å×ÀÌºí¿¡ ÀúÀåµÈ ¾ÏÈ£ÀÇ salt·Î ÁöÁ¤µÈ ÇØ½ÃµÈ ¾ÏÈ£¿Í ºñ±³ÇÏ´Â Äڵ尡 Æ÷ÇԵǾî ÀÖ½À´Ï´Ù

ÇØ½ÃµÈ ÆÛÁñ¿¡ ´ëÇÑ ¶Ç ´Ù¸¥ Ãø¸éÀº AddSecureUser.aspx¿¡¼­ º¼ ¼ö ÀÖ½À´Ï´Ù. ÀÌ ÆäÀÌÁö¸¦ »ç¿ëÇϸé salt·Î ÁöÁ¤µÇ¾î ÇØ½ÃµÈ ¾ÏÈ£¸¦ »ý¼ºÇÏ°í À̸¦ SecureUsers Å×ÀÌºí¿¡ ÀúÀåÇÒ ¼ö ÀÖ½À´Ï´Ù. BestLogin.aspx ¹× AddSecureUser.aspx´Â ¸ðµÎ ¡°Ç¥ 6¡±¿¡ Ç¥½ÃµÈ °Í°ú °°ÀÌ SaltedHash Ŭ·¡½º ¶óÀ̺귯¸®ÀÇ Äڵ带 »ç¿ëÇÕ´Ï´Ù. Jeff Prosise°¡ ¸¸µç ÀÌ ÄÚµå´Â System.Web.Security ³×ÀÓ½ºÆäÀ̽ºÀÇ FormsAuthentication.HashPasswordForStoringInConfigFile ¸Þ¼­µå¸¦ »ç¿ëÇÏ¿© ¾ÏÈ£ Çؽø¦ ¸¸µé°í System.Security.Cryptography ³×ÀÓ½ºÆäÀ̽ºÀÇ RNGCryptoServiceProvider.GetNonZeroBytes ¸Þ¼­µå¸¦ »ç¿ëÇÏ¿© 16¹ÙÀÌÆ®ÀÇ ÀÓÀÇ salt °ª(Convert.ToBase64StringÀ» »ç¿ëÇÏ¿© ¹®ÀÚ¿­·Î º¯È¯ÇÒ °Ü¿ì 24 ¹®ÀÚ°¡ µÊ)À» ¸¸µé ¼ö ÀÖ½À´Ï´Ù.

SQL injections °ø°Ý°ú Á÷Á¢ °ü·ÃµÇÁö´Â ¾ÊÁö¸¸ BestLogin.aspx´Â ¿¬°á ¹®ÀÚ¿­ÀÇ ¾Ïȣȭ¶ó´Â ¶Ç ´Ù¸¥ ÃÖ¼±ÀÇ º¸¾È ±¸Çö ¹æ¹ýÀ» º¸¿© ÁÝ´Ï´Ù. ¿¬°á ¹®ÀÚ¿­Àº Æ÷ÇÔµÈ µ¥ÀÌÅͺ£À̽º °èÁ¤ ¾ÏÈ£°¡ µé¾î ÀÖ´Â °æ¿ì BestLogin.aspx¿¡¼­¿Í °°ÀÌ Æ¯È÷ Áß¿äÇÏ°Ô º¸È£µÇ¾î¾ß ÇÕ´Ï´Ù. µ¥ÀÌÅͺ£À̽º¿¡ ¿¬°áÇÏ·Á¸é ¿¬°á ¹®ÀÚ¿­ÀÇ ¾ÏÈ£¸¦ Çص¶ÇØ¾ß Çϱ⠶§¹®¿¡ ¿¬°á ¹®ÀÚ¿­Àº ÇؽÃÇÒ ¼ö ¾ø½À´Ï´Ù. ±× ´ë½Å ¿¬°á ¹®ÀÚ¿­À» ¾ÏȣȭÇØ¾ß ÇÕ´Ï´Ù. ´ÙÀ½Àº Web.config¿¡ ÀúÀåµÇ¾î ÀÖ°í BestLogin.aspx¿¡¼­ »ç¿ëµÇ´Â ¾ÏȣȭµÈ ¿¬°á ¹®ÀÚ¿­À» º¸¿© ÁÝ´Ï´Ù.

<add key="cnxNWindBest" value="AQAAANCMnd8BFdERjHoAwE/ Cl+sBAAAAcWMZ8XhPz0O8jHcS1539LAQAAAACAAAAAAADZgAAqAAAABAAAABdodw0YhWfcC6+ UjUUOiMwAAAAAASAAACgAAAAEAAAALPzjTRnAPt7/W8v38ikHL5IAAAAzctRyEcHxWkzxeqbq/ V9ogaSqS4UxvKC9zmrXUoJ9mwrNZ/ XZ9LgbfcDXIIAXm2DLRCGRHMtrZrp9yledz0n9kgP3b3s+ X8wFAAAANmLu0UfOJdTc4WjlQQgmZElY7Z8" />
private void cmdLogin_Click(object sender, System.EventArgs e) {
try {
// Grab the encrypted connection string and decrypt it
string strCnx = SecureConnection.GetCnxString("cnxNWindBest");
        // Establish connection to database
using (SqlConnection cnx = new SqlConnection(strCnx))
{
SqlParameter prm;
            cnx.Open();
            // Execute sproc to retrieved hashed password for this user
string strHashedDbPwd;
            SqlCommand cmd = new SqlCommand("procGetHashedPassword", cnx);
cmd.CommandType = CommandType.StoredProcedure;
prm = new SqlParameter("@username", SqlDbType.VarChar,50);
prm.Direction = ParameterDirection.Input;
prm.Value = txtUser.Text;
cmd.Parameters.Add(prm);
            strHashedDbPwd = (string) cmd.ExecuteScalar();
            if (strHashedDbPwd.Length>0) {
// Verify that hashed user-entered password is the same
// as the hashed password from the database
if (SaltedHash.ValidatePassword(txtPassword.Text,
strHashedDbPwd)) {
FormsAuthentication.RedirectFromLoginPage(
txtUser.Text, false);
}
else {
lblMsg.Text = "Login attempt failed.";
}
}
else {
lblMsg.Text = "Login attempt failed.";
}
}
}
catch {
lblMsg.Text = "Login attempt failed.";
}
}
public class SaltedHash {
static public bool ValidatePassword (string password,
string saltedHash) {
// Extract hash and salt string
const int LEN = 24;
string saltString = saltedHash.Substring(saltedHash.Length - LEN);
string hash1 = saltedHash.Substring(0, saltedHash.Length - LEN);
// Append the salt string to the password
string saltedPassword = password + saltString;
// Hash the salted password
string hash2 =
FormsAuthentication.HashPasswordForStoringInConfigFile(
saltedPassword, "SHA1");
// Compare the hashes
return (hash1.CompareTo(hash2) == 0);
}
static public string CreateSaltedPasswordHash (string password) {
// Generate random salt string
RNGCryptoServiceProvider csp = new RNGCryptoServiceProvider();
byte[] saltBytes = new byte[16];
csp.GetNonZeroBytes(saltBytes);
string saltString = Convert.ToBase64String(saltBytes);
// Append the salt string to the password
string saltedPassword = password + saltString;
// Hash the salted password
string hash =
FormsAuthentication.HashPasswordForStoringInConfigFile(
saltedPassword, "SHA1");
// Append the salt to the hash
return hash + saltString;
}
}
Ç¥ 6

public class SecureConnection {
static public string GetCnxString(string configKey) {
string strCnx;
        try {
// Grab encrypted connection string from web.config
string strEncryptedCnx =
ConfigurationSettings.AppSettings[configKey];
            // Decrypt the connection string
DataProtector dp = new
DataProtector(DataProtector.Store.USE_MACHINE_STORE);
byte[] dataToDecrypt =
Convert.FromBase64String(strEncryptedCnx);
strCnx =
Encoding.ASCII.GetString(dp.Decrypt(dataToDecrypt,null));
}
catch {
strCnx="";
}
        return strCnx;
}
}
Ç¥ 7
 
BestLoginÀº ¡°Ç¥ 7¡±¿¡¼­¿Í °°ÀÌ SecureConnection Ŭ·¡½º·ÎºÎÅÍ GetCnxString ¸Þ¼­µå¸¦ È£ÃâÇÏ¿© cnxNWindBest AppSetting °ªÀ» °Ë»öÇÏ°í À̸¦ ´ÙÀ½ ÄÚµå·Î ¾ÏÈ£ Çص¶ÇÕ´Ï´Ù. string strCnx = SecureConnection.GetCnxString("cnxNWindBest");
¼ø¼­´ë·Î SecureConnection Ŭ·¡½º´Â È£ÃâÀ» Win32 DPAPI(µ¥ÀÌÅÍ º¸È£ API)·Î ·¡ÇÎÇÏ´Â DataProtect Ŭ·¡½º ¶óÀ̺귯¸®(¿©±â¿¡ Ç¥½ÃµÇÁö´Â ¾ÊÁö¸¸ ÀÌ ¹®¼­ÀÇ ´Ù¿î·Îµå¿¡ Æ÷ÇԵǾî ÀÖÀ½)¸¦ È£ÃâÇÕ´Ï´Ù. DPAPIÀÇ ´Ù¾çÇÑ ±â´É Áß Çϳª´Â »ç¿ëÀÚ¸¦ À§ÇØ ¾Ïȣȭ Å°¸¦ °ü¸®ÇÏ´Â °ÍÀÔ´Ï´Ù. DataProtect Ŭ·¡½º ¶óÀ̺귯¸® ¹× ÀÌ ¶óÀ̺귯¸®¸¦ »ç¿ëÇÒ ¶§ °í·ÁÇØ¾ß ÇÏ´Â Ãß°¡ ¿É¼Ç¿¡ ´ëÇÑ ÀÚ¼¼ÇÑ ³»¿ëÀº Microsoft ÆÐÅÏ ¹× ¿¬½À °¡À̵å Áß ÇϳªÀÎ "º¸¾ÈÀûÀÎ ASP.NET ÀÀ¿ë ÇÁ·Î±×·¥ ÀÛ¼º: ÀÎÁõ, ±ÇÇÑ ºÎ¿© ¹× º¸¾È Åë½Å (¿µ¹®)"À» ÂüÁ¶ÇϽʽÿÀ.
http://msdn.microsoft.com/ko-kr/library/ms994921(en-us).aspx
 
EncryptCnxString.aspx ÆäÀÌÁö¸¦ »ç¿ëÇÏ¸é ½Ã½ºÅÛ Æ¯Á¤ ¾ÏȣȭµÈ ¿¬°á ¹®ÀÚ¿­À» ¸¸µé¾î¼­ ±¸¼º ÆÄÀÏ¿¡ ºÙ¿© ³ÖÀ» ¼ö ÀÖ½À´Ï´Ù. ÀÌ ÆäÀÌÁö´Â ±×¸² 3¿¡ Ç¥½ÃµÇ¾î ÀÖ½À´Ï´Ù. ¹°·Ð, ¾ÏȣȭÇϰųª ÇؽÃÇØ¾ß ÇÏ´Â ±â¹Ð Á¤º¸¿¡´Â ¾ÏÈ£ ¹× ¿¬°á ¹®ÀÚ¿­ ¿Ü¿¡µµ ½Å¿ë Ä«µå ¹øÈ£ ¹× ÇØÄ¿¿¡°Ô ³ëÃâµÉ °æ¿ì À§ÇèÇÒ ¼ö ÀÖ´Â ±âŸ ¸ðµç Á¤º¸°¡ Æ÷ÇԵ˴ϴÙ. ASP.NET 2.0¿¡´Â ¾ÏÈ£ ÇØ½Ì ¹× ¿¬°á ¹®ÀÚ¿­ ¾Ïȣȭ¸¦ ´Ü¼øÇÏ°Ô ¸¸µé¾î ÁÖ´Â ¿©·¯ ±â´ÉÀÌ Æ÷ÇԵǾî ÀÖ½À´Ï´Ù.
 

±×¸² 3

7. ¾ÈÀüÇÑ ½ÇÆÐ

·±Å¸ÀÓ ¿¹¿Ü¸¦ ÀûÀýÇÏ°Ô Ã³¸®ÇÏÁö ¸øÇÒ °æ¿ì¿¡µµ ÇØÄ¿´Â À̸¦ ¾Ç¿ëÇÒ ¼ö ÀÖ½À´Ï´Ù. µû¶ó¼­ ¸ðµç ÇÁ·Î´ö¼Ç Äڵ忡 ¿¹¿Ü 󸮱⸦ Æ÷ÇÔ½ÃÅ°´Â °ÍÀÌ Áß¿äÇÕ´Ï´Ù. ¶ÇÇÑ Ã³¸®µÈ ¿¹¿Ü ¹× 󸮵ÇÁö ¾ÈÀº ¿¹¿Ü´Â Ç×»ó ÇØÄ¿¿¡°Ô µµ¿òÀÌ µÉ ¼ö ÀÖ´Â Á¤º¸¸¦ ÃÖ¼ÒÇÑÀ¸·Î¸¸ Á¦°øÇØ¾ß ÇÕ´Ï´Ù. ó¸®µÈ ¿¹¿ÜÀÇ °æ¿ì ¿À·ù ¸Þ½ÃÁö¿¡¼­ ¿ø·¡ »ç¿ëÀÚ¿¡ ´ëÇÑ À¯¿ë¼º°ú ¾ÇÀÇÀûÀÎ ÇØÄ¿¿¡°Ô ³Ê¹« ¸¹Àº Á¤º¸¸¦ Á¦°øÇÏÁö ¾Ê´Â º¸¾È¼º °£ÀÇ ±ÕÇüÀ» ¸ÂÃß¾î¾ß ÇÕ´Ï´Ù.

󸮵ÇÁö ¾ÊÀº ¿¹¿ÜÀÇ °æ¿ì¿¡´Â ÄÄÆÄÀÏ ¿ä¼Ò(Web.config ÆÄÀÏ)ÀÇ µð¹ö±× Ư¼ºÀ» False·Î ¼³Á¤ÇÏ°í customErrors ¿ä¼ÒÀÇ ¸ðµå Ư¼ºÀ» On ¶Ç´Â RemoteOnly·Î ¼³Á¤ÇÏ¿© ÇØÄ¿¿¡°Ô ÃÖ¼ÒÇÑÀÇ Á¤º¸¸¸ Ç¥½ÃµÇµµ·Ï ÇØ¾ß ÇÕ´Ï´Ù. ¿¹¸¦ µé¾î ´ÙÀ½À» º¸½Ê½Ã¿À. <compilation defaultLanguage="c#" debug="false" /> <customErrors mode="RemoteOnly" />

RemoteOnly ¼³Á¤Àº localhost·ÎºÎÅÍ »çÀÌÆ®¿¡ ¾×¼¼½ºÇÏ´Â »ç¿ëÀÚ¿¡°Ô´Â À¯¿ëÇÑ ¿À·ù ¸Þ½ÃÁö¸¦ Á¦°øÇÏ°í ¿ø°Ý À§Ä¡·ÎºÎÅÍ »çÀÌÆ®¿¡ ¾×¼¼½ºÇÏ´Â ´Ù¸¥ »ç¿ëÀÚ¿¡°Ô´Â ¿¹¿Ü¿¡ ´ëÇÑ ¾î¶² À¯¿ëÇÑ Á¤º¸µµ ³ëÃâ½ÃÅ°Áö ¾Ê´Â ÀϹÝÀûÀÎ ¿À·ù ¸Þ½ÃÁö¸¦ Á¦°øÇϵµ·Ï º¸ÀåÇÕ´Ï´Ù. ·ÎÄà »ç¿ëÀÚ¸¦ Æ÷ÇÔÇÑ ¸ðµç »ç¿ëÀÚ¿¡°Ô ÀÏ¹Ý ¿À·ù ¸Þ½ÃÁö¸¦ Ç¥½ÃÇϵµ·Ï ÇÏ·Á¸é On ¼³Á¤À» »ç¿ëÇϽʽÿÀ. ÇÁ·Î´ö¼Ç ȯ°æ¿¡¼­´Â Off ¼³Á¤À» Àý´ë·Î »ç¿ëÇÏÁö ¸¶½Ê½Ã¿À.

8. °á·Ð
SQL injections °ø°ÝÀº º¸¾È ½Ã½ºÅÛ¿¡ ħÀÔÇÏ¿© µ¥ÀÌÅ͸¦ ÈÉÄ¡°Å³ª, º¯°æ ¶Ç´Â »èÁ¦ÇÒ ¿ì·Á°¡ Àֱ⠶§¹®¿¡ ÀÀ¿ë ÇÁ·Î±×·¥ °³¹ßÀÚ°¡ ½ÅÁßÇÏ°Ô ´Ù·ç¾î¾ß ÇÏ´Â ¹®Á¦ÀÔ´Ï´Ù. »ç¿ëÇÏ´Â ASP.NET ¹öÀü°ú´Â °ü°è¾øÀÌ ÀÌ·¯ÇÑ °ø°Ý¿¡´Â ³Ê¹«³ª ½±°Ô Ãë¾àÇØÁú ¼ö ÀÖ½À´Ï´Ù. ½ÇÁ¦·Î ASP.NETÀ» »ç¿ëÇÏÁö ¾Ê´Â °æ¿ì¿¡µµ SQL injections °ø°Ý¿¡ ½±°Ô ´çÇÒ ¼ö ÀÖ½À´Ï´Ù. Windows Forms ÀÀ¿ë ÇÁ·Î±×·¥°ú °°ÀÌ »ç¿ëÀÚ ÀÔ·Â µ¥ÀÌÅ͸¦ »ç¿ëÇÏ¿© µ¥ÀÌÅͺ£À̽º¸¦ Äõ¸®ÇÏ´Â ¸ðµç ÀÀ¿ë ÇÁ·Î±×·¥Àº ÀáÀçÀûÀ¸·Î injections °ø°ÝÀÇ ´ë»óÀÌ µÉ ¼ö ÀÖ½À´Ï´Ù.

SQL injections °ø°ÝÀ¸·ÎºÎÅÍ ÀÚ½ÅÀ» º¸È£ÇÏ´Â ¹æ¹ýÀº ±×·¸°Ô ¾î·ÆÁö ¾Ê½À´Ï´Ù. ¸ðµç »ç¿ëÀÚ ÀԷ¿¡ ´ëÇÑ À¯È¿¼ºÀ» °Ë»ç ¹× È®ÀÎÇÏ°í, µ¿Àû SQLÀ» Àý´ë·Î »ç¿ëÇÏÁö ¾Ê°í, ÃÖ¼Ò ±ÇÇÑÀ¸·Î °èÁ¤À» »ç¿ëÇÏ°í, ÇØ´ç ±â¹Ð Á¤º¸¸¦ Çؽà ¶Ç´Â ¾ÏȣȭÇÏ°í, ÇØÄ¿¿¡°Ô À¯¿ëÇÑ Á¤º¸¸¦ Á¦°øÇÏÁö ¾Êµµ·Ï °ÅÀÇ Á¤º¸¸¦ Ç¥½ÃÇÏÁö ¾Ê´Â ¿À·ù ¸Þ½ÃÁö¸¦ Á¦°øÇÏ´Â ÀÀ¿ë ÇÁ·Î±×·¥Àº SQL injections °ø°ÝÀ» ¸Å¿ì È¿°úÀûÀ¸·Î ¹æÁöÇÒ ¼ö ÀÖ½À´Ï´Ù. ¿©·¯ °èÃþÀÇ °ø°Ý ¹æ¾î ¹æ¹ýÀ» »ç¿ëÇÒ °æ¿ì ÇϳªÀÇ ¹æ¹ýÀÌ ½ÇÆÐÇÏ´õ¶óµµ °è¼ÓÇؼ­ º¸È£ »óŸ¦ À¯ÁöÇÒ ¼ö ÀÖ½À´Ï´Ù.
 
  Oops-firewall ¼³Ä¡ ¹× »ç¿ë¹æ¹ý
  ModSecurity¸¦ È°¿ëÇÑ ¾ÆÆÄÄ¡ À¥¼­¹ö º¸¾È °­È­ °¡À̵å





ȸ»ç¼Ò°³ °³ÀÎÁ¤º¸Ãë±Þ¹æħ ÀÌ¿ë¾à°ü À̸ÞÀÏÁÖ¼Ò ¹«´Ü¼öÁý°ÅºÎ CONTACT US IDC ¾àµµ
ȸ»ç¼Ò°³ °³ÀÎÁ¤º¸Ãë±Þ¹æħ ÀÌ¿ë¾à°ü À̸ÞÀÏÁÖ¼Ò ¹«´Ü¼öÁý°ÅºÎ CONTACT US IDC ¾àµµ ȸ»ç¼Ò°³ °³ÀÎÁ¤º¸Ãë±Þ¹æħ ÀÌ¿ë¾à°ü À̸ÞÀÏÁÖ¼Ò ¹«´Ü¼öÁý°ÅºÎ CONTACT US IDC ¾àµµ