For a great tutorial on how to N-O-T develop a mobile payment application, take a look at the sample code provided by Mastercard here. For more Mastercard Open API goodness, check these examples out here and here.
In this snippet from the sample code, they are providing a placeholder for hardcoding your companyID and companyPassword in plaintext string format:
final double amount = Float.valueOf(amountInput.getText().toString());
final String currency = "USD";
final String companyId = "your-company-id-here";
final String companyPassword = "your-company-password-here";
final String messageId = "your-message-id-here";
final String settlementId = "your-settlement-id-here";
final String cardHolderName = cardHolderNameInput.getText().toString();
final String accountNumber = cardNumberInput.getText().toString();
final String expiryMonth = expirationMonthInput.getText().toString();
final String expiryYear = expirationYearInput.getText().toString();
And below, we append this to our request and send!!
request.append("<MerchantIdentity>");
request.append("<CompanyId>");
request.append(companyId);
request.append("</CompanyId>");
request.append("<CompanyPassword>");
request.append(companyPassword);
request.append("</CompanyPassword>");
request.append("</MerchantIdentity>");
Hardcoding your credentials is NEVER (I repeat, NEVER) a good idea. Please don't do this. Your companyID and companyPassword are used for both processing payments, and processing refunds. Fully decompiling an Android application is extremely trivial, as demonstrated here. There are also applications floating around that allow 1-click rooting. You don't have to be an uber elite expert to do this stuff.
What concerns me most is the de-centralization of highly sensitive information. This is a bigtime mobile trend. If you are writing code like this and giving 50 employees an Android phone or tablet, what is the likelihood that at least 1 of them will end up getting lost at some point? What is the likelihood that at least one of those devices will get owned at some point? What is the likelihood that a malicious employee would take this information and rob your company blind? Pretty high, in my opinion.
In a perfect world, this type of architecture would involve a very simple upstream web service and web server where the credentials could be stored in a secure way. The web service would ask for the credit card information, and THAT'S IT. There's less of a risk of data leakage with one target instead of 50.
There are lots of very important design aspects to consider when rolling out this type of capability. If you are in the business of losing money, then copy and paste this code and begin processing mobile payments. And don't even consider putting something like this in the Android market because I will find it ;)
-Jack
10 comments:
Nice! Love the hard-coded username and password. Especially since those are trivial to dump from the disassembled DEX bytecode. String constant dumping is one of the things we scripted in the Smart Phones Dumb Apps demo code
Crappy example code is a huge source of insecurity because of all the cut-and-paste reuse. Great work calling out the Mastercard folks on this.
--Dan
dan _at_ denimgroup.com
I like the part where they're using floating point to represent currency. That's pretty much a dead giveaway that the coder has never written code to handle money before.
@Dan- Thanks. Trainwreck waiting to happen. I'm sure PCI is loving it. This type of scenario has surely led to some binge drinking within PCI.
You would think a payment AUTHORITY would be a little more responsible and careful with their guidance. I can totally see an explosion of ad supported mobile payment apps hitting the market. Copy, paste, slap AdMob into the app, done =)
-Jack
Understand every line in this blog, good explainative language are used. Very useful for the future,added good article for more information about this blog.
Can you break this down for me, what would be the best practice?
You say that hard coding credentials is wrong, which sounds right (problems changing them, etc.). But if the application needs credentials to work, and you don't want to make a user enter them at every start up, is hard coding them that much worse than storing them in a config?
I guess a better practice would be to encrypt the credentials and store them in a config file, yes? That will not stop a determined attacker that can decompile the app, but it does make it harder than running 'strings'.
You mention that in a perfect world they would only send the CHD, not the credentials to the payment gateway. But doesn't that just push the problem over, because now you need a separate set of credentials from the mobile app to the web service? If you don't, how do you prevent anyone from sending in refunds to the web service?
thanks,
Marc
Jack,
New to android coding I was also wondering about the certificate checking in the example. Is that part of the libraries or will an invalid cert be ignored by the application leaving it open to MiTM.
@dmartin.org- Thanks for the feedback, and thanks for understanding that this wasn't intended as bashing but rather constructive criticism for the greater good. Some comments:
3) That's really the only true way to do it in a reasonably secure way. The client code was the problem, not the server-side stuff. It's an interesting challenge due to the distributed nature of the beast. At the same time, this has been done for years with POS systems. As someone else mentioned, with what both you and I suggested you would be pushing the problem to a different tier. But at the same time, you have much more control of that tier and can implement fine grained controls such as time limited sessions, granular logging, etc. Shouldn't hamper the mobile experience at all if done correctly.
We had a little bit of dialogue today on the OWASP Mobile Security Project mailing list regarding this. It would be awesome to engage your expertise and the expertise of your team to drive open security standards and exchange ideas. Here is the link:
http://www.owasp.org/index.php/OWASP_Mobile_Security_Project#tab=Project_About
And the mailing list:
https://lists.owasp.org/mailman/listinfo/owasp-mobile-security-project
My contact information is listed on the project page as well. The mailing list is a great place to converse, but please feel free to get in touch offline as well.
-Jack
The link got truncated somehow. Here it is again
Mobile Project
Very good post, and certainly gives gives credibility to the phrase "Smart Phones, Dumb Apps.
Post a Comment