?
Solved

Directory Security issue in IIS using .asp pages

Posted on 2007-08-09
26
Medium Priority
?
245 Views
Last Modified: 2013-11-19
I need some help with security.

I have a website that stores all invoices in a virtual invoice folder.
Usuers cannot browse the invoices but they can substitute a number and see an invoice not meant for them.

I need to fix this and I am not sure how.

Current;y users log in on the website with a user/pass and that is checked against an access database, they are shown data that belongs to them.  When they want to view an invoice, they click on a link and that lionk spawns a script that resides on the server that checks to see if the invoice they are requesting belongs to them.

The link is something like this:

www.mysite.com/getinvoice.asp?INV=999999.pdf 

However, if they type
www.mysite.com/invoices/999998.pdf 
they will get the invoice that doesn't belong to them regardless.

I also have to send out notices that tell members that they have new invoices and I have tio list them like so:
www.mysite.com/invoices/999997.pdf 
www.mysite.com/invoices/999998.pdf 
www.mysite.com/invoices/999999.pdf 

that aslo can be "hacked" to show any invoice.

How can I secure this so that they are :
1. Required to go to my login page at least once during the session
2. Denied access to other invoices.

I have a script that checks for that but I do not know how to get it to fire when someone has a direct address.

HELP!
0
Comment
Question by:gormly
  • 13
  • 13
26 Comments
 
LVL 38

Accepted Solution

by:
PaulHews earned 375 total points
ID: 19665192
>Current;y users log in on the website with a user/pass and that is checked against an access database

If users log in using windows domain usernames (turn off anonymous access in IIS, and use Basic Authentication with SSL over the Internet or Integrated Windows Authentication on your local network) then you can use Windows NTFS permissions on separate files or folders to control who has access to what.

The other way is to restrict access to the files and only allow download through the ASP script.  So the files will be in a folder that is restricted from your web site, but you can validate the download through a script similar to this:

if Check(strUser, strFilename) = True Then  'Whatever logic you have to validate users for filenames...

    Set objFSO = Server.CreateObject("Scripting.FileSystemObject")
    Set objTS = objFSO.OpenTextFile(Server.MapPath("InvoiceFolder/" & strFile))

    Response.Buffer = True

    Response.ContentType = "application/pdf"
    Response.AddHeader "Content-disposition", "attachment; filename=" & strFile

    Do While Not objTS.AtEndOfStream
      strChunk = objTS.Read(32)
      strTmp = "" 
      For i = 1 to Len(strChunk)
          strTmp = strTmp & ChrB(Asc(Mid(strChunk, i, 1)))
      Next
      Response.BinaryWrite strTmp
      Response.Flush
    loop

    objTS.Close
    Set objTS = Nothing
    Set objFSO = Nothing
Else
    Response.Redirect "noaccess.html"
End If

0
 
LVL 1

Author Comment

by:gormly
ID: 19665240
The probelm with that is I HAVE to use the link:  http://www.mysite.com/invoices/999999.pdf


My boss is adament about it, how do I redirect http://www.mysite.com/invoices/999999.pdf to a script file?
0
 
LVL 38

Expert Comment

by:PaulHews
ID: 19665893
>The probelm with that is I HAVE to use the link:
Then start authenticating against Windows users and lock everything down with NTFS.  Bonus, it's a very secure method.

OR

Use a custom 404 page script to redirect to the authentication script.  I would Google some examples for you, but right now my Internet connection is connecting very selectively....  The basic idea is that instead of a HTML page for 404 errors, you put in an ASP script... You detect what the incoming requests are, and when they match a certain pattern (like http://www.mysite.com/invoices/999999.pdf) then you extract the numeric portion from the request URL, do your checking as above, and serve up the bytes as above...
0
What Security Threats Are We Predicting for 2018?

Cryptocurrency, IoT botnets, MFA, and more! Hackers are already planning their next big attacks for 2018. Learn what you might face, and how to defend against it with our 2018 security predictions.

 
LVL 38

Expert Comment

by:PaulHews
ID: 19668967
Using URL rewrites
http://evolvedcode.net/content/code_smart404/guide-rewrites.asp


Note this next article uses server.transfer... You would not use that if you want the URL to look like invoices/999999.pdf.  Instead, handle the full request in your custom 404 script.

Extending Your Page Names
http://www.asp101.com/articles/wayne/extendingnames/default.asp
0
 
LVL 1

Author Comment

by:gormly
ID: 19668995
Hello Paul
I appreciate the attempt but really, that is the problem I am having in a nutshell.

I HAVE an asp script that will do that, my trouble is I don't know how to fire it from a 404.
I said above,
>>"I have a script that checks for that but I do not know how to get it to fire when someone has a direct address."


How can I get a 404 file to get the variable of the invoice number and store it?

when someone types http://www.mysite.com/invoices/999999.pdf and they are not logged in I need them to log in and then be redirected to the invoice.  

One idea is to have the \invoice folder empty and fire the 404 which will strip the invoice number save to a session variable and then redirect to a login.. the login will redirect to the invoice if the login correctly.

Great Idea.. I just dont know how to implement it.

0
 
LVL 38

Expert Comment

by:PaulHews
ID: 19669188
>I HAVE an asp script that will do that, my trouble is I don't know how to fire it from a 404.

What you have is a script that redirects to an unsecured file resource on your server.  In order to secure those resources, you have to remove them from the path of the web server, and serve them up as bytes when a request comes in and doesn't find them...

>I don't know how to fire it from a 404.

You do that from IIS.  It is explained in the second article.

>How can I get a 404 file to get the variable of the invoice number and store it?

In the custom 404 script, you get the request.  That's going to look like this:

<%
 Dim strPage, strID
 strPage = Request.ServerVariables("SCRIPT_NAME")
'Check for URL http://www.mysite.com/invoices/999999.pdf 
If LCase(Left(strPage, Len(strStart))) = strStart And LCase(Right(strPage, Len(strEnd))) = strEnd Then
    strID = Mid(strPage, Len(strStart) + 1, Len(strPage) - Len(strStart) - Len(strEnd))
    'This is the number.  Now check user credentials and get the file
   
End If
 
%>
0
 
LVL 38

Expert Comment

by:PaulHews
ID: 19669222
Correction, missing a couple of pieces:

<%
Dim strPage, strID, strStart, strEnd
'Some say QUERY_STRING... I can only get this to work in IIS6.
 strPage = Request.ServerVariables("SCRIPT_NAME")  
'Check for URL /invoices/999999.pdf
strStart = "/invoices/"
strEnd = ".pdf"
If LCase(Left(strPage, Len(strStart))) = strStart And LCase(Right(strPage, Len(strEnd))) = strEnd Then
    strID = Mid(strPage, Len(strStart) + 1, Len(strPage) - Len(strStart) - Len(strEnd))
    'This is the number.  Now get the user credentials, and the file if valid.

End If
 
%>
0
 
LVL 1

Author Comment

by:gormly
ID: 19669808
Ok, this works... I made a system that does the redirect but the security problem still exists.
That fixed the email issue, now they must login to get an invoice.

but once they get one invoice.. and if they are set to open PDFs in a browser (most are) they now see the location of the invoices in the browser bar and can still change the numbers to get others members invoices, becasue the addres bar shows the normally redirected directory name

arrggh! back to square one!

I guess the problem is how do I get around showing the user what the address to the pdf is?


0
 
LVL 1

Author Comment

by:gormly
ID: 19669901
Note:  I tried using server.transer but it turns up junk like the pdf is opening in the browser as a text file.
0
 
LVL 38

Expert Comment

by:PaulHews
ID: 19669916
>I guess the problem is how do I get around showing the user what the address to the pdf is?

You don't.   Don't give access to the PDF's except through the script.  Take the invoice folder out of the web path.
0
 
LVL 1

Author Comment

by:gormly
ID: 19669933
are you serious?
there is no method to allow access and hide the urls?

if so that stinks.
0
 
LVL 38

Expert Comment

by:PaulHews
ID: 19671678
>are you serious?
>there is no method to allow access and hide the urls?

I've described two methods you can use to secure the files.  Both allow you to enter the URL as http://www.mysite.com/invoices/999999.pdf and both allow the user only to open the files that they are approved for.  So, what was your question again?

0
 
LVL 1

Author Comment

by:gormly
ID: 19671847
Paul

with all respect, I don't see how you have given me two methods.

yes, I can now make sure only autheticated users can access their invoices by using a direct link like:
http://www.mysite.com/invoices/999999.pdf 

But the problem is that once they get to the link http://www.mysite.com/invoices/999999.pdf 
all they need to do is change the 999999.pdf in the browser toolbar to get another file because any 404 redirect script I use in the http://www.mysite.com/invoices folder with return the "true" address when the pdf opens in the users browser.

in other words

The link they getnin email is: http://www.mysite.com/invoices/999999.pdf 
They go to that link and it fires the 404 script, the script grabs the invoice number (999999) and checks to see if the user is logged in, if not, it redirects to the login which then sends them to the real invoice: http://www.mysite.com/realinvoicefolder/999999.pdf 

The Problem is that on the last step the browser now displays http://www.mysite.com/realinvoicefolder/999999.pdf  instead of http://www.mysite.com/invoices/999999.pdf 
and all they have to do to get another invoice that doesn't belong to them is change the invoice number in the address bar URL

http://www.mysite.com/realinvoicefolder/8888888.pdf 

do you see what I mean?
There is no way to hide the last step.. the real address of the pdf file.

unless I missed something???
0
 
LVL 38

Expert Comment

by:PaulHews
ID: 19672043
>The link they getnin email is: http://www.mysite.com/invoices/999999.pdf
They go to that link and it fires the 404 script, the script grabs the invoice number (999999) and checks to see if the user is logged in, if not, it redirects to the login which then sends them to the real invoice: http://www.mysite.com/realinvoicefolder/999999.pdf <

The problem is that you are sending them to a file resource.  That is not what I suggested.  There should be no real invoice folder on the web server.

When the 404 script gets the request, it sends back the bytes of the PDF, that are retrieved by the script.  Redirecting in any way will cause the URL rewriting to fail and the new address will likely be revealed.

I just ran a test locally, not as a 404 script, but this ASP script sends back a PDF file to the browser.  Note that the IIS user has to have read permissions on the PDF folder, or you will get permission errors.




<%
    Set objFSO = Server.CreateObject("Scripting.FileSystemObject")
    Set objTS = objFSO.OpenTextFile("C:\Temp\Test.pdf")

    Response.Buffer = True

    Response.ContentType = "applications/vnd.pdf"
    Response.AddHeader "Content-disposition", "attachment; filename=test.pdf"

    Do While Not objTS.AtEndOfStream
      strChunk = objTS.Read(32)
      strTmp = ""
      For i = 1 to Len(strChunk)
          strTmp = strTmp & ChrB(Asc(Mid(strChunk, i, 1)))
      Next
      Response.BinaryWrite strTmp
      Response.Flush
    loop

    objTS.Close
    Set objTS = Nothing
    Set objFSO = Nothing

%>

0
 
LVL 1

Author Comment

by:gormly
ID: 19672528
Oh, I see... I did miss that  : <
I will test it and see what happens.

Thanks Paul.
0
 
LVL 38

Expert Comment

by:PaulHews
ID: 19672663
I just noticed you mentioned above that you were getting the file sent back as text in the browser.  I think having the right content type defined is the key... applications/vnd.pdf works okay.  Also, the filename in the Content-Disposition header has to end in PDF.
0
 
LVL 1

Author Comment

by:gormly
ID: 19683516
Paul

This is not working for me, I am still getting "text" sent to the browsers.
If you have a moment... Here is the code:
      
If Session("LOGIN") = False then

      ' not logged in, send them to login and save some
      session("INVOICE")=request("INVOICE")
      session("referer") =Request.ServerVariables ("URL")
      response.redirect("http://www.mywebsite.com/login.asp")
      
else

      INVOICE=Request("INVOICE")
      'this checks to see if the request is coming from a link
      if INVOICE = "" or ISNULL(INVOICE) then
            'otherwise we need to get the invoice number from the saved session varible in login.asp
            INVOICE=session("INVOICE")
      else
      end if
      
end if

INVOICEstrip=replace(INVOICE,".pdf","")

set objConn = server.createobject("adodb.connection")
objConn.open "Provider=Microsoft.Jet.OLEDB.4.0;" & _
      "Data Source=c:\databases\;" & _
       "Extended Properties=""DBASE IV;"";"
            sqlstat="SELECT *  FROM MyDatabase WHERE INVOICE= '"+INVOICEstrip+"' and ACCO='" + session("user") + "'"
set rs = objConn.execute (sqlstat)


if Not rs.eof then'

while not.rs.eof
      pdf = INVOICEstrip
      
            Set objFSO = Server.CreateObject("Scripting.FileSystemObject")
            Set objTS = objFSO.OpenTextFile("C:\invoices\" & INVOICEstrip & ".pdf")
            Response.Buffer = True
            Response.ContentType = "applications/vnd.pdf"
            Response.AddHeader "Content-disposition", "attachment; filename=" & INVOICEstrip & ".pdf"
            Do While Not objTS.AtEndOfStream
              strChunk = objTS.Read(32)
              strTmp = ""
              For i = 1 to Len(strChunk)
                    strTmp = strTmp & ChrB(Asc(Mid(strChunk, i, 1)))
              Next
              Response.BinaryWrite strTmp
              Response.Flush
            loop
            objTS.Close
            Set objTS = Nothing
            Set objFSO = Nothing
                  
      rs.movenext
      wend
      
else
response.redirect("99999z.pdf")
end if





I even tried this totally seperate from any other code to see what I would get and I still get the text....
I know the "text" is the actual pdf, but the browser is not seeing it as a pdf.
0
 
LVL 38

Expert Comment

by:PaulHews
ID: 19684325
Is the code above the full script?   Nothing else above or below?
0
 
LVL 1

Author Comment

by:gormly
ID: 19684540
yes.. full
nothing else above or below.


I am testing a copy to temp then redirect directory solution right now and although it works like a charm, it still isn't the cats meow. I have to dump all the copied pdfs on a regular basis and thats not a great solution.

I would love to get this working correctly, but I have almost lost hope.
:<

0
 
LVL 38

Expert Comment

by:PaulHews
ID: 19684676
Does this cause the same problem?

http://notbono.dnsalias.com/temp/test.asp
0
 
LVL 1

Author Comment

by:gormly
ID: 19684788
no it opened fine.

I assume you're using the same code?
0
 
LVL 38

Expert Comment

by:PaulHews
ID: 19684923
Yes, so this rules out that it's a browser issue at least.  What version of IIS are you using?

>while not.rs.eof

Why are you doing looping through the recordset?  Don't you expect only a single record?
0
 
LVL 1

Author Comment

by:gormly
ID: 19685002
I am using IIS 6.0

and the "while not" is just a left over from copied code, once it works I will make it a bit tighter.
0
 
LVL 38

Expert Comment

by:PaulHews
ID: 19685168
IIS 6 will work fine with this.  Try to get the simplest example working first.  You might try clearing the cache before running it.  
0
 
LVL 1

Author Comment

by:gormly
ID: 19685262
I am going to try it from a complely different system.
I am running to another office to remove any local influences thast might be screwing things up.

I know this should work

0
 
LVL 1

Author Closing Comment

by:gormly
ID: 31407613
This first answer is a working solution for most situations.
0

Featured Post

 The Evil-ution of Network Security Threats

What are the hacks that forever changed the security industry? To answer that question, we created an exciting new eBook that takes you on a trip through hacking history. It explores the top hacks from the 80s to 2010s, why they mattered, and how the security industry responded.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Experts Exchange expands question security options for members.
Phishing emails are a popular malware delivery vehicle for attack.  While there are many ways for an attacker to increase the chances of success for their phishing emails, one of the most effective methods involves spoofing the message to appear to …
The is a quite short video tutorial. In this video, I'm going to show you how to create self-host WordPress blog with free hosting service.
This video Micro Tutorial shows how to password-protect PDF files with free software. Many software products can do this, such as Adobe Acrobat (but not Adobe Reader), Nuance PaperPort, and Nuance Power PDF, but they are not free products. This vide…
Suggested Courses

839 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question