https://crocs.fi.muni.cz @CRoCS_MUNI PA193 - Secure coding principles and practices Secure coding introduction + language level vulnerabilities: Buffer overflow, type overflow, strings Petr Švenda svenda@fi.muni.cz @rngsec Centre for Research on Cryptography and Security, Masaryk University Please provide feedback for any issue found in slides here: https://drive.google.com/file/d/1S5euWbzlYnAG8qq1PPb_99MZWLKh_3r4/view?usp=sharing https://crocs.fi.muni.cz @CRoCS_MUNI COURSE TRIVIA: PA193_00_COURSE_ORGANISATION_2022.PPTX | PA193 - Secure coding2 https://crocs.fi.muni.cz @CRoCS_MUNI3 • Place/upvote questions in slido while listening to lecture video • We will together discuss these during every week lecture Q&A (every Monday)#pa193_2022 I PA193 - Introductory info https://crocs.fi.muni.cz @CRoCS_MUNI | PA193 - Secure coding 4 Problem? https://nvd.nist.gov/ https://crocs.fi.muni.cz @CRoCS_MUNI What is the cost of insecure software • Increased risk and failures due to generally increased usage of computers • Fixing bug in released version is more expensive – Testing, announcements… • Liability laws – Need to notify, settlements, GDPR... • Reputation loss – (unfortunately, does not seem to be at the moment) • Cost of defense is decreasing – better training (like this course ☺), automated tools, development methods, new langs… – But complexity of software is also increasing 5 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI There is HUGE market for (undisclosed) vulnerabilities 6 | PA193 - Secure coding • Up to millions of dollars for single undisclosed exploit • Payed over defined period it stays undiscovered – Product vendor is not notified and cannot fix • Ethics: export restrictions to sell exploit kits – But HackingTeam, Cellebrite, NSO… https://zerodium.com/program.html https://crocs.fi.muni.cz @CRoCS_MUNI What software security means? • Use of generic good development and security practices – Education, testing, defence in depth, code review… – Safety (random errors CRC good enough) vs. security (intentional attacker recomputing CRC after malicious change) – Security is process, not product (Secure Development Lifecycle) • Have systematic deployment, maintenance and mitigation of issues (including the security relevant) – Monitor, triage, fix, update process, detection of issues in 3rd party libs… • Usability - easy to use right, hard to misuse – Hard for developers to misuse or misconfigure (API security…), hard for end-users to make a mistake – If misuse, then limit its impact, secure defaults… • Automated and manual review and testing – Continuous integration, pentesting, security code review • Language-specific issues and procedures, corresponding tooling and automation – Buffer overflow (C/C++), code injection (Java)… • Use of secure cryptographic primitives – Cryptographic libraries, random numbers, password handling, secure channels, key distribution… 7 | PA193 - Secure codingIcon made by geotatah, eucalypt, freepik from www.flaticon.com https://crocs.fi.muni.cz @CRoCS_MUNI Defensive programming • Term coined by Kernighan and Plauger, 1981 – “writing the program so it can cope with small disasters” – talked about in introductory programming courses • Practice of coding with the mind-set that errors are inevitable, and something will always go wrong – prepare program for unexpected behavior and inputs – prepare program for easier testing and bug diagnostics • Defensive programming targets mainly unintentional errors (not intentional attacks) – But increasingly given security connotation 8 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI WHERE TO LEARN ABOUT BUGS AND RESULTING VULNERABILITIES? | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Attacker goals and related vulnerabilities • Bug is unintended and unwanted behavior which attacker can use to: 1. Steal some data (keys in memory, content of files…) 2. Bypass some protection (access rights, authentication, hijack session) 3. Execute malicious code (custom payload, ROP…) 4. Cause denial of service (resource exhaustion, infinite loop, regex) 5. … • The real attack (exploit) often combines multiple steps – E.g., DoS to deplete memory resulting in failed dynamic allocation, then write to null pointer, then execute malicious payload | PA19 3 Secu 10 https://crocs.fi.muni.cz @CRoCS_MUNI Where to find relevant bug patterns and info • Taxonomies of vulnerabilities (systematic) – Common Weakness Enumeration (CWE) https://cwe.mitre.org/ – Wikipedia (https://en.wikipedia.org/wiki/Memory_safety ...) • List of real vulnerabilities detected and reported (complex real-world examples) – Common Vulnerabilities and Exposures (CVE) https://cve.mitre.org/ • Lists of frequent bugs (prioritization) – The CWE Top 25 https://cwe.mitre.org/top25/archive/2020/2020_cwe_top25.html – OWASP TOP10 https://owasp.org/www-project-top-ten/ – HackerOne TOP 10 https://www.hackerone.com/top-10-vulnerabilities – Veracode TOP 10 by language https://info.veracode.com/state-of-software-security-volume-11- flaw-frequency-by-language-infosheet-resource.html – Significant differences between usage domains (web vs. embedded devices) • Bug patterns searched for by specific tool (understanding bugs & tool used) – E.g., FindSecurityBugs (Java): https://find-sec-bugs.github.io/bugs.htm 11 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Common Weakness Enumeration (CWE) • Taxonomy of vulnerabilities https://cwe.mitre.org/ • List of vulnerability categories, sub-categories, examples and mitigation – Baseline for vulnerability identification, mitigation and prevention – Itself is great study material including examples • Example CWE-124 Buffer Underwrite – https://cwe.mitre.org/data/definitions/124.html 12 | PA193 - Secure coding int main() { // ... strncpy(destBuf, &srcBuf[find(srcBuf, ch)], 1024); } https://crocs.fi.muni.cz @CRoCS_MUNI | PA19 3 Secu 13 https://cwe.mitre.org/data/definitions/124.html https://crocs.fi.muni.cz @CRoCS_MUNI | PA19 3 Secu 14 https://crocs.fi.muni.cz @CRoCS_MUNI Frequent bugs – worth of prioritization (CWE/CVE) | PA193 - Secure coding 15 https://cwe.mitre.org/top25/archive/2020/2020_cwe_top25.html • Score by presence in real vulnerabilities – Common Vulnerabilities and Exposures (CVE) https://crocs.fi.muni.cz @CRoCS_MUNI Frequent bugs – worth of prioritization (web) 16 | PA193 - Secure coding • Be aware: – Differences between software domains (web, OS kernel, libraries…) – Detection bias – bugs we can more easily detect seem to be more frequent https://owasp.org/www-project-top-ten/ https://crocs.fi.muni.cz @CRoCS_MUNI Example: Injection (1. OWASP TOP 10, 3. CWE Top 25) • Goal: Return records from DB for the provided customer ID (custID) String query = "SELECT * FROM accounts WHERE custID='" + request.getParameter("id") + “’”; • User/attacker will provide customer ID as follows: – http://example.com/app/accountView?id=' or '1'='1 • Resulting SQL command after expansion (executed by database engine) – SELECT * FROM accounts WHERE custID='' or '1'='1’ • Mitigation – Don’t try to detect and fix injection by checking input arguments yourself! – Read about defenses, use dedicated secure API (e.g., PreparedStatement in this case) – https://cheatsheetseries.owasp.org/cheatsheets/SQL_Injection_Prevention_Cheat_Sheet.html | PA193 - Secure coding 17 https://owasp.org/www-project-top-ten/2017/A1_2017-Injection https://crocs.fi.muni.cz @CRoCS_MUNI CWE flaw types by language | PA19 3 Secu 18 https://info.veracode.com/state-of-software-security-volume-11-flaw-frequency-by-language-infosheet-resource https://crocs.fi.muni.cz @CRoCS_MUNI Bugs patterns searched by tools • Bug description • Example of vulnerable code • References to other lists – CWE, OWASP… 19 | PA193 - Secure coding https://find-sec-bugs.github.io/bugs.htm https://crocs.fi.muni.cz @CRoCS_MUNI Digging deeper and learning more… • Read top-level categories from CWE Software Development – Get broad overview https://cwe.mitre.org/data/definitions/699.html • Read details about top vulnerabilities from OWASP or CWE list – Likely the most common ones • Find, read about and test several vulnerabilities in detail – Which applies to your favorite language (e.g., Java) – And target domain (e.g., server database backend) in detail – Learn more about system by understanding all details • Experiment with several automatic tools to detect such vulnerabilities • Think like an attacker, have fun ☺ | PA19 3 Secu 20 https://crocs.fi.muni.cz @CRoCS_MUNI Vulnerability disclosure basics • Bug, Vulnerability, Proof of Concept (PoC), Exploit – Bug = buffer overflow – Vulnerability = execution of malicious code – Proof of Concept = tool triggering buffer overflow and crashing program – Exploit = tool trigger buffer overflow, executing custom payload and creating root account on target machine • Public disclosure, Uncoordinated public disclosure, Zero-day • Responsible disclosure, disclosure period/deadline, bugbounty • Whitehats, blackhats, red teams, blue teams 21 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI HOW TO PREVENT, DETECT AND MITIGATE CODE BUGS? 22 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI How to prevent, detect and mitigate code bugs? 1. Protection on the source code level – E.g., languages with/without implicit protection (containers/languages with array boundary checking) – E.g., input checking, sanitization, safe alternatives to vulnerable function like safe string manipulation 2. Protection by extensive testing (source code/binary/bytecode level) – E.g., automatic detection by static and dynamic checkers – E.g., code review, security testing 3. Protection by compiler (+ compiler flags) – E.g., runtime checks introduced by compiler (stack protection) 4. Protection by execution environment – E.g., DEP, ASLR, sandboxing, hardware isolation... 5. Protection by defense in depth – All above in systematic secure development lifecycle, multiple layers of defense 23 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Microsoft’s Secure Development Lifecycle (SDL) 24 | PA193 - Secure coding https://www.microsoft.com/en-us/securityengineering/sdl/practices https://crocs.fi.muni.cz @CRoCS_MUNI Use secure-by default languages and libraries • Ideally, language is already designed to be more secure – Partially true for newer languages like Go or Rust – But new systematic issues may be found later • Libraries – Use functions from platform standard API (e.g., AndroidKeyStore provider) – Use libraries which are hard to be used incorrectly • E.g., Libsodium’s crypto_secretbox_easy() vs. OpenSSL vs. own custom code – Monitor used libraries/packages for new vulnerabilities (dependbot) • Don’t design or implement own libraries especially not cryptographic – Developing own library code likely means repeating other’s mistakes – Cryptographic code is extremely difficult to code securely 25 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Use of more secure versions of functions • Consider language removing whole class of vulnerabilities – E.g., Rust to replace memory-related errors in C • If language is fixed, then use more secure / hardened functions – E.g., Secure C library ISO/IEC 9899:2011 – E.g., java.lang.Math precise arithmetic extensions – E.g., Smart pointers in C++ • Follow best practices, standards and coding standards – E.g., CERT C Coding Standard https://www.securecoding.cert.org/confluence/display/seccode/CERT+C+Coding+Standard – (there are many of them, pick for your domain and/or already used in project) 26 | PA193 - Secure coding char *gets( char *buffer ); char *gets_s( char *buffer, size_t sizeInCharacters ); https://crocs.fi.muni.cz @CRoCS_MUNI Utilize hardening by compiler and platform • Attack: Write attacker’s code on stack (e.g., via buffer overflow) and execute it • Protection: Data Execution Prevention (DEP) – memory pages with nonexecutable bit set (checked by CPU when using IP) • Attack: Learn where sensitive info is placed, read from that address (or write) • Protection: Address Space Layout Randomization (ASLR) – addresses are changed for every program run (hard to predict exact position) • Attack: Change return address and jump into unexpected functions (Returnoriented programming (ROP)) • Protection: Control flow integrity – build graph of allowed jumps from source code, enforce during runtime 27 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI AUTOMATION AND TOOLING 28 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Static vs. dynamic analysis • Static analysis – Static Application Security Testing (SAST) – Examine program’s code without executing it – Can examine both source code and compiled code • source code is easier to understand (more metadata) – Can be applied on unfinished code – Manual code audit is kind of “static” analysis • Dynamic analysis – Code is executed = program is “running” – Input values are supplied, internal memory is examined… – Code must compile/run, code coverage by inputs is crucial • Important: no single tool will ever catch all issues 29 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Automated analysis tools limitations • Don’t expect tools to catch all issues! • Overall program architecture is not understood – sensitivity of program path – impact of errors on other parts • Application semantics is not understood – Is string returned to the user? Can string also contain passwords? • Social context is not understood – Who is using the system? High entropy keys encrypted under short guessable password? 30 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Always design for testability • “Code that isn't tested doesn't work - this seems to be the safe assumption.” Kent Beck • Code written in a way which is easier to test – Proper decomposition, unit tests, mock objects – Source code annotations (with subsequent analysis) • Code with extensive quality tests is easier to analyze by static and dynamic tools • References – https://en.wikipedia.org/wiki/Design_For_Test – http://www.agiledata.org/essays/tdd.html 31 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI CONTINUOUS INTEGRATION | PA193 - Secure coding 32 https://crocs.fi.muni.cz @CRoCS_MUNI Tests, Continuous integration… • Running tools manually is insufficient for continuously developed projects • Include static and dynamic analysis into Continuous Integration process • Static analysis can be run on unfinished code chunks even before commit – On developer side, on commits before merge… • Dynamic analysis requires sufficient code coverage => quality tests • Time-consuming analysis can be run “overnight” on server (after push) – Or continuously like non-stop fuzzing of the current version of application • Tools for automatic monitoring of vulnerable components – Well-known packages, libraries used by your project with known vulnerability – E.g., GitHub’s Dependabot 33 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Continuous Integration: GitHub&Travis CI example 34 | PA193 - Secure coding GitHub COMMIT Branch: Test Web hook Artifacts Tests Tests OK https://crocs.fi.muni.cz @CRoCS_MUNI CI: adding code analysis (e.g., CppCheck, Coverity) | PA193 - Secure coding GitHub COMMIT Branch: Test Web hook Tests 35 https://crocs.fi.muni.cz @CRoCS_MUNI Dependabot (GitHub) 36 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI TYPICAL PROBLEMS FROM REAL WORLD 37 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Typical issues – where theory meets practice ☺ • Insufficient knowledge/education of developers (mature developer would not do majority of issues) – Education is time-consuming and expensive (complement with tooling, security champions) • Legacy code – Too many issues reported by tools to fix – Fix itself can break things (so developers reluctant to fix what is “not” broken) • Missing specification of the expected behavior – Missing analysis, changing implementation target – If implemented code is successful, then is used elsewhere in different condition (original assumptions will be invalidated) • Adding security only later (“Functionality first!”) – It's happening all the time • Heavy dependance on 3rd party libs – No direct control over code, vulnerabilities outside our codebase, possibly unmaintained code (fix means fork) – But re-implementing a wheel is usually a worse issue • Using open-source code can be tricky, you usually must care about: – Licenses (tools to help with like Whitesource, Blackduck) – Open vulnerabilities, time-to-fix, how active is community – In mature organizations, there's usually a open-source governance program that helps developers with choosing the right OSS tools 38 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Typical issues – where theory meets practice ☺ • Human issues – No problem before we started to look for them – Hard to admit own failures (If I cannot break it, nobody can. “But it is not exploitable”). – Unresponsive/threatening companies – Same with knowledge, lack of maturity, code guidelines, frameworks • Security economics – Problem is known, yet not fixed – these who need to pay for fix are not these who will suffer – Frequently, developer’s KPI is functionality, not security • Customers do not want to update (new version can break things) – Big upgrades mean big risks, small releases/upgrades can help with that • Trust, but Verify – Many companies do not deliver what they promised – Security is very common area: insecure updates, insecure installation procedures (curl & chmod & sudo) • Improper adoption of new tech – protobuf, JSON, JWT, serialization... – New languages (like "go") are cool, but you need to learn new tooling, test frameworks, CI/CD pipelines, dependencies, ... 39 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI40 | PA193 - Secure coding Questions #pa193_2022 https://crocs.fi.muni.cz @CRoCS_MUNI DIGGING DEEPER… 41 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Motivation problem • Quiz – what is insecure in given program? • Can you come up with attack? • Classic buffer overflow • Detailed exploitation demo during labs this week 42 | PA193 - Secure coding #define USER_INPUT_MAX_LENGTH 20 char buffer[USER_INPUT_MAX_LENGTH]; bool isAdmin = false; gets(buffer); https://crocs.fi.muni.cz @CRoCS_MUNI Process memory layout 43 | PA193 - Secure coding http://www.drdobbs.com/security/anatomy-of-a-stack-smashing-attack-and-h/240001832# https://crocs.fi.muni.cz @CRoCS_MUNI Stack memory layout 44 | PA193 - Secure coding http://www.drdobbs.com/security/anatomy-of-a-stack-smashing-attack-and-h/240001832# https://crocs.fi.muni.cz @CRoCS_MUNI Stack overflow 45 | PA193 - Secure coding http://www.drdobbs.com/security/anatomy-of-a-stack-smashing-attack-and-h/240001832# https://crocs.fi.muni.cz @CRoCS_MUNI https://en.wikipedia.org/wiki/Memory_safety 46 | PA193 - Secure coding Are other languages also affected by memory overflow vulnerabilities? Is Java, Python… affected? https://crocs.fi.muni.cz @CRoCS_MUNI Type-overflow vulnerabilities - motivation • Quiz – what is insecure in given program? • Can you come up with attack? • And what about following variant? – Be aware: char can be both signed (x64) or unsigned (ARM) 47 | PA193 - Secure coding for (unsigned char i = 10; i >= 0; i--) { /* ... */ } for (char i = 10; i >= 0; i--) { /* ... */ } https://crocs.fi.muni.cz @CRoCS_MUNI Type overflow – basic problem • Types are having limited range for the values – char: 256 values, int: 232 values – add, multiplication can reach lower/upper limit – char value = 250 + 10 == ? • Signed vs. unsigned types – for (unsigned char i = 10; i >= 0; i--) {/* ... */ } • Type value will underflow/overflow – CPU overflow flag is set – but without active checking not detected in program • Occurs also in higher-level languages (Java…) 48 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI EXAMPLE: MAKE HUGE MONEY WITH TYPE OVERFLOW 49 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Make HUGE money with type overflow • Bitcoin block 74638 (15th August 2010) 50 | PA193 - Secure coding CBlock(hash=0000000000790ab3, ver=1, hashPrevBlock=0000000000606865, hashMerk nTime=1281891957, nBits=1c00800e, nNonce=28192719, vtx=2) CTransaction(hash=012cd8, ver=1, vin.size=1, vout.size=1, nLockTime=0) CTxIn(COutPoint(000000, -1), coinbase 040e80001c028f00) CTxOut(nValue= 50.51000000, scriptPubKey=0x4F4BA55D1580F8C3A8A2C7) CTransaction(hash=1d5e51, ver=1, vin.size=1, vout.size=2, nLockTime=0) CTxIn(COutPoint(237fe8, 0), scriptSig=0xA87C02384E1F184B79C6AC) CTxOut(nValue=92233720368.54275808, scriptPubKey=OP_DUP OP_HASH160 0xB7 CTxOut(nValue=92233720368.54275808, scriptPubKey=OP_DUP OP_HASH160 0x15 vMerkleTree: 012cd8 1d5e51 618eba Block hash: 0000000000790ab3f22ec756ad43b6ab569abf0bddeb97c67a6f7b1470a7ec1c Transaction hash: 1d5e512a9723cbef373b970eb52f1e9598ad67e7408077a82fdac194b653 Input transaction (with 0.5BTC) https://blockexplorer.com/tx/237fe8348fc77ace11049931 058abb034c99698c7fe99b1cc022b1365a705d39 Mining block reward (was 50BTC at 2010, is 12.50BTC now) 2 output transactions (each with 9*1010 BTC) !!! Should have been rejected by miners as value(output) >> value(input), but was not! https://crocs.fi.muni.cz @CRoCS_MUNI More details: Payment in Bitcoin • Payment example – You can’t say “I pay 1 bitcoin to address A1” – You must take previous valid block B with amount X – Then create transaction which will split value from B into 1 send to A1 and X-1 send to (your) A2 • Transaction fee – payed to miners as incentive to incorporate your transaction into block – Was 0 or very small in 2010 (is higher now) – Miners fee is difference (CTxIn – (CTxOut)) 51 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Bug dissection • Bitcoin code uses integer encoding of numbers with fixed position of decimal point (INT64) – Smallest fraction of BTC is one Satoshi (sat) = 1/108 BTC – 33.54 BTC == 33.54 * 108 => 3354000000 • BTW: Why using float numbers is not a good idea? • CTxOut value:92233720368.54275808 BTC = 0x7ffffffffff85ee0 • INT64_MAX = 0x7fffffffffffffff • Sum of 2 CTx = 0xfffffffffff0bdc0 (overflow) = -100000010 = -0.01BTC – Difference between input & output interpreted as miner fee 52 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Type overflow – Bitcoin 53 | PA193 - Secure coding #include #include using namespace std; // Works for Visual Studio compiler, replace __int64 with int64 for other compilers int main() { const __int64 valueMaxInt64 = 0x7fffffffffffffffLL; const float COIN = 100000000; // should be __int64 as well, made float for simple printing __int64 valueIn = 50000000; // value of input transaction CTxIn cout << "CTxIn = " << valueIn / COIN << endl; __int64 valueOut1 = 9223372036854275808L; // first out cout << "CTxOut1 = " << valueOut1 / COIN << endl; __int64 valueOut2 = 9223372036854275808L; // second out cout << "CTxOut2 = " << valueOut2 / COIN << endl; __int64 valueOutSum = valueOut1 + valueOut2; // sum which overflow cout << "CTxOut sum = " << valueOutSum / COIN << endl; // Difference between input and output is interpreted as fee for a miner (0.01 BTC) __int64 fee = valueIn - valueOutSum; cout << "Miner fee = " << fee / COIN << endl; return 0; } https://crocs.fi.muni.cz @CRoCS_MUNI Bug impact (CVE-2010-5139) • 2 * 92233720368.54275808 + 0.01 BTC artificially created in single transaction • Detected 1.5 hours after the transaction occurred • Code patched and blockchain hard forked to abandon branch with malicious transaction – Hard fork was possible in early days of Bitcoin, would be more difficult now – BTW: Ethereum had hard fork after $60M DAO hack • https://en.bitcoin.it/wiki/Common_Vulnerabilities_and_Exposures#CVE-2010-5139 • https://bitcointalk.org/index.php?topic=822.0 54 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI BugFix – proper checking for overflow 55 | PA193 - Secure coding https://github.com/bitcoin/bitcoin/commit/d4c6b90ca3f9b47adb1b2724a0c3514f80635c84#diff-118fcbaaba162ba17933c7893247df3aR1013 https://crocs.fi.muni.cz @CRoCS_MUNI Questions • When exactly overflow happens? • Why mining reward was 50.51 and not exactly 50? – CTxOut(nValue= 50.51000000 • How to check for type overflow? 56 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI END OF EXAMPLE 57 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Type overflow – example with dynalloc 58 | PA193 - Secure coding typedef struct _some_structure { float someData[1000]; } some_structure; void demoDataTypeOverflow(int totalItemsCount, some_structure* pItem, int itemPosition) { // See http://blogs.msdn.com/oldnewthing/archive/2004/01/29/64389.aspx some_structure* data_copy = NULL; int bytesToAllocation = totalItemsCount * sizeof(some_structure); printf("Bytes to allocation: %d\n", bytesToAllocation); data_copy = (some_structure*) malloc(bytesToAllocation); if (itemPosition >= 0 && itemPosition < totalItemsCount) { memcpy(&(data_copy[itemPosition]), pItem, sizeof(some_structure)); } else { printf("Out of bound assignment"); return; } free(data_copy); } Basic idea: • Data to be copied into newly allocated mem. • Computation of required size type-overflow • Too small memory chunk is allocated • Copy will write behind allocated memory https://crocs.fi.muni.cz @CRoCS_MUNI SOURCE CODE PROTECTIONS COMPILER PROTECTIONS PLATFORM PROTECTIONS 59 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Safe add and mult operations in C/C++ • Compiler-specific non-standard extensions of C/C++ • GCC: __builtin_add_overflow, __builtin_mul_overflow … – Result returned as third (pointer passed) argument – Returns true if overflow occurs – https://gcc.gnu.org/onlinedocs/gcc/Integer-Overflow-Builtins.html • MSVC: SafeInt wrapper template (for int, char…) – Overloaded all common operations (drop in replacement) – Returns SafeIntException if overflow/underflow – https://msdn.microsoft.com/en-us/library/dd570023.aspx 60 | PA193 - Secure coding bool __builtin_add_overflow (type1 a, type2 b, type3 *res) #include using namespace msl::utilities; // Normal use SafeInt c1 = 1; SafeInt c2 = 2; c1 = c1 + c2; https://crocs.fi.muni.cz @CRoCS_MUNI Safe add and mult operations in Java 61 | PA193 - Secure coding • Java SE 8 introduces extensions to java.lang.Math • ArithmeticException thrown if overflow/underflow public static int addExact(int x, int y) public static long addExact(long x, long y) public static int decrementExact(int a) public static long decrementExact(long a) public static int incrementExact(int a) public static long incrementExact(long a) public static int multiplyExact(int x, int y) public static long multiplyExact(long x, long y) public static int negateExact(int a) public static long negateExact(long a) public static int subtractExact(int x, int y) public static long subtractExact(long x, long y) public static int toIntExact(long value) https://crocs.fi.muni.cz @CRoCS_MUNI Format string vulnerabilities - motivation • Quiz – what is insecure in given program? • Can you come up with attack? 62 | PA193 - Secure coding int main(int argc, char * argv[]) { printf(argv[1]); return 0; } https://crocs.fi.muni.cz @CRoCS_MUNI Format string vulnerabilities • Wide class of functions accepting format string – printf("%s", X); – resulting string is returned to user (= potential attacker) – formatting string can be under attacker’s control – variables formatted into string can be controlled • Resulting vulnerability – memory content from stack is formatted into string – possibly any memory if attacker control buffer pointer 63 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Information disclosure vulnerabilities • Exploitable memory vulnerability leading to read access (not write access) – attacker learns some information from the memory • Direct exploitation – secret information (cryptographic key, password...) • Precursor for next step (very important with DEP&ASLR) – module version – current memory layout after ASLR (stack/heap pointers) – stack protection cookies (/GS) 64 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Format string vulnerability - example • Example retrieval of security cookie and return address 65 | PA193 - Secure coding int main(int argc, char* argv[]) { char buf[64] = {}; sprintf(buf, argv[1]); printf("%s\n", buf); return 0; } argv[1] submitted by an attacker E.g., %x%x%x….%x Stack content is printed Including security cookie and RA Don’t let user/attacker to provide own formatting strings https://crocs.fi.muni.cz @CRoCS_MUNI Non-terminating functions - example • What is wrong with following code? 66 | PA193 - Secure coding int main(int argc, char* argv[]) { char buf[16]; strncpy(buf, argv[1], sizeof(buf)); return printf("%s\n",buf); } https://crocs.fi.muni.cz @CRoCS_MUNI strncpy - manual 67 | PA193 - Secure coding http://www.cplusplus.com/reference/cstring/strncpy/?kw=strncpy https://crocs.fi.muni.cz @CRoCS_MUNI Non-terminating functions for strings • strncpy • snprintf • vsnprintf • mbstowcs • MultiByteToWideChar • Non-null terminated Unicode string more dangerous – C-string processing stops on first zero – any binary zero (ASCII) – 16-bit aligned wide zero character (UNICODE) • wcsncpy • snwprintf • vsnwprintf • wcstombs • WideCharToMultiByte 68 | PA193 - Secure coding Null termination specific for C, but terminating/separating characters relevant in any other language https://crocs.fi.muni.cz @CRoCS_MUNI Heap overflow 69 | PA193 - Secure coding Buffer overflow in allocation 1 overwrites header for allocation 2 (and possibly other) Linked list between allocated blocks Felix "FX" Lindner, http://www.h-online.com/security/features/A-Heap-of-Risk-747220.html Corrupted allocation 2 data are later processed by unlink() function https://crocs.fi.muni.cz @CRoCS_MUNI Heap overflow – more details • Assumption: buffer overflow possible for buffer at heap • Problem: – attacker needs to write his pointer to memory later used as jump – no return pointer (jump) is stored on heap (as was the case for stack) • Different mechanism for misuse – overwrite malloc metadata (few bytes before allocated block) • only next, prev, size and used can be manipulated • fake header (hdr) for fake block is created – let unlink function to be called (merge free blocks) • fake block is also merged during merge operation • hdr->next->next->prev = hdr->next->prev; 70 | PA193 - Secure coding address on stack that will be interpreted later as jump pointer address of attacker’s code https://crocs.fi.muni.cz @CRoCS_MUNI Secure C library – selected functions • Formatted input/output functions – gets_s – scanf_s, wscanf_s, fscanf_s, fwscanf_s, sscanf_s, swscanf_s, vfscanf_s, vfwscanf_s, vscanf_s, vwscanf_s, vsscanf_s, vswscanf_s – fprintf_s, fwprintf_s, printf_s, printf_s, snprintf_s, snwprintf_s, sprintf_s, swprintf_s, vfprintf_s, vfwprintf_s, vprintf_s, vwprintf_s, vsnprintf_s, vsnwprintf_s, vsprintf_s, vswprintf_s – functions take additional argument with buffer length • File-related functions – tmpfile_s, tmpnam_s, fopen_s, freopen_s • takes pointer to resulting file handle as parameter • return error code 71 | PA193 - Secure coding char *gets( char *buffer ); char *gets_s( char *buffer, size_t sizeInCharacters ); https://crocs.fi.muni.cz @CRoCS_MUNI Secure C library – selected functions • Environment, utilities – getenv_s, wgetenv_s – bsearch_s, qsort_s • Memory copy functions – memcpy_s, memmove_s, strcpy_s, wcscpy_s, strncpy_s, wcsncpy_s • Concatenation functions – strcat_s, wcscat_s, strncat_s, wcsncat_s • Search functions – strtok_s, wcstok_s • Time manipulation functions... 72 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI CERT C/C++ Coding Standard • CERT C Coding Standard – https://www.securecoding.cert.org/confluence/display/seccode/CERT+C+Coding+Standard • CERT C++ Coding Standard – https://www.securecoding.cert.org/confluence/pages/viewpage.action?pageId=637 • Cern secure coding recommendation for C – https://security.web.cern.ch/security/recommendations/en/codetools/c.shtml • Smashing the stack in 2011 – https://paulmakowski.wordpress.com/2011/01/25/smashing-the-stack-in-2011/ 73 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Secure C library • Secure versions of commonly misused functions – bounds checking for string handling functions – better error handling • Also added to new C standard ISO/IEC 9899:2011 • Microsoft Security-Enhanced Versions of CRT Functions – MSVC compiler issue warning C4996, more functions then in C11 • Secure C Library – http://docwiki.embarcadero.com/RADStudio/XE3/en/Secure_C_Library – https://docs.microsoft.com/en-us/cpp/c-runtime-library/security-enhanced-versions-of-crt-functions – https://docs.microsoft.com/en-us/cpp/c-runtime-library/security-features-in-the-crt – http://www.drdobbs.com/cpp/the-new-c-standard-explored/232901670 74 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI SOURCE CODE PROTECTIONS COMPILER PROTECTIONS PLATFORM PROTECTIONS 75 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI MSVC Compiler security flags - /RTC • Nice overview of available protections – http://msdn.microsoft.com/en-us/library/bb430720.aspx • Visual Studio → Configuration properties → C/C++ → All options • Run-time checks – /RTCu switch • uninitialized variables check – /RTCs switch • stack protection (stack pointer verification) • initialization of local variables to a nonzero value • detect overruns and underruns of local variables such as arrays – /RTC1 == /RTCsu 76 | PA193 - Secure coding /RTC is intended for DEBUG mode, unused for RELEASE https://crocs.fi.muni.cz @CRoCS_MUNI – randomized cookie between local variables and return address – function prolog (add security cookie) – and epilog (check cookie) 77 | PA193 - Secure coding Stack without canary word http://www.drdobbs.com/security/anatomy-of-a-stack-smashing-attack-and-h/240001832# Canary word (CY) https://crocs.fi.muni.cz @CRoCS_MUNI MSVC Compiler security flags - /GS • /GS switch (added from 2003, improves in time) – http://msdn.microsoft.com/en-us/library/8dbf701c.aspx – multiple different protections against buffer overflow – mostly focused on stack protection • /GS protects: – return address of function – address of exception handler – vulnerable function parameters (arguments) – some of the local buffers (GS buffers) • /GS protection is (automatically) added only when needed – to limit performance impact, decided by compiler (/GS rules) – #pragma strict_gs_check(on) - enforce strict rules application 78 | PA193 - Secure coding /GS is applied in both DEBUG and RELEASE modes https://crocs.fi.muni.cz @CRoCS_MUNI /GS Security cookie (‘canary’) - details • /GS Security cookie – random DWORD number generated at program start – master cookie stored in .data section of loaded module – xored with function return address (pointer encoding) – corruption results in jump to undefined value • __security_init_cookie – http://msdn.microsoft.com/en-us/library/ms235362.aspx 79 | PA193 - Secure coding Stack after /GS Function parameters Function return address Frame pointer Cookie Exception Handler frame Locally declared variables and buffers Callee save registers Stack without /GS Function parameters Function return address Frame pointer Exception Handler frame Locally declared variables and buffers Callee save registers https://crocs.fi.muni.cz @CRoCS_MUNI /GS buffers • Buffers with special protection added – http://msdn.microsoft.com/en-us/library/8dbf701c.aspx – automatically and heuristically selected by compiler • Applies to: – array larger than 4 bytes, more than two elements, element type is not pointer type – data structure with size more than 8 bytes with no pointers – buffer allocated by using the _alloca function • stack-based dynamic allocation – any class or structure with GS buffer 80 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI /GS – vulnerable parameters • Protection of function’s vulnerable parameters – parameters passed into function – copy of vulnerable parameters (during fnc’s prolog) placed below the storage area for any other buffers – variables prone to buffer overflow are put on higher address so their overflow will not overwrite other local variables • Applies to: – pointer – C++ reference – C-structure containing pointer – GS buffer 81 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Is /GS protection bulletproof? • Return address of X can be overwritten inside Y • Incorrect jump is executed only later after X ends • … 82 | PA193 - Secure coding Function parameters Function return address (of Y == X) Frame pointer Cookie Exception Handler frame Locally declared variables and buffers Callee save registers Function parameters Function return address (of X) Frame pointer Cookie Exception Handler frame Locally declared variables and buffers Callee save registers Y X https://crocs.fi.muni.cz @CRoCS_MUNI /GS – what is NOT protected • /GS compiler option does not protect against all buffer overrun security attacks • Corruption of address in vtable – (table of addresses for virtual methods) • Example: buffer and a vtable in an object, a buffer overrun could corrupt the vtable • Functions with variable arguments list (...) 83 | PA193 - Secure coding Automatic tools add vital protections, but are NOT replacement for secure defensive programming https://crocs.fi.muni.cz @CRoCS_MUNI /GS – more references • Compiler Security Checks In Depth (MS) – http://msdn.microsoft.com/en-us/library/aa290051%28v=vs.71%29.aspx • /GS cookie effectiveness (MS) – http://blogs.technet.com/b/srd/archive/2009/03/16/gs-cookie-protection-effectiveness-and- limitations.aspx • Windows ISV Software Security Defenses – http://msdn.microsoft.com/en-us/library/bb430720.aspx • How to bypass /GS cookie – https://www.corelan.be/index.php/2009/09/21/exploit-writing-tutorial-part-6-bypassing-stack- cookies-safeseh-hw-dep-and-aslr/ 84 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI GCC compiler - StackGuard & ProPolice • StackGuard released in 1997 as extension to GCC – but never included as official buffer overflow protection • GCC Stack-Smashing Protector (ProPolice) – patch to GCC 3.x – included in GCC 4.1 release – -fstack-protector (string protection only) – -fstack-protector-all (protection of all types) – on some systems enabled by default (OpenBSD) • -fno-stack-protector (disable protection) 85 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI GCC compiler & ProPolice - example 86 | PA193 - Secure coding http://www.drdobbs.com/security/anatomy-of-a-stack-smashing-attack-and-h/240001832# https://crocs.fi.muni.cz @CRoCS_MUNI GCC -fno-stack-protector 87 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Security cookie in MSVC • CANARY word (security cookie) – https://kallanreed.wordpress.com/2015/02/14/disabling-the- stack-cookie-generation-in-visual-studio-2013/ – XOR value from __security_cookie address with frame base pointer (EBP) => CANARY value (stored on stack) – Check before return: CANARY XOR EBP =? *__security_cookie • vcruntime.h 88 | PA193 - Secure coding void __cdecl __security_check_cookie(_In_ uintptr_t _StackCookie); __declspec(noreturn) void __cdecl __report_gsfailure(_In_ uintptr_t _StackCookie); push ebp mov ebp, esp sub esp, 80 ; 00000050H mov eax, DWORD PTR ___security_cookie xor eax, ebp mov DWORD PTR __$ArrayPad$[ebp], eax push ebx push esi push edi ; 6 : char buffer[10]; ; 7 : strcpy(buffer, "aaaaaaaaaaaaaaaaaaaaaaaaaaa") push OFFSET ??_C@_0BM@CINAKCFB@aaaaaaaaaaaa lea eax, DWORD PTR _buffer$[ebp] push eax call _strcpy add esp, 8 pop edi pop esi pop ebx mov ecx, DWORD PTR __$ArrayPad$[ebp] xor ecx, ebp call @__security_check_cookie@4 mov esp, ebp pop ebp ret 0 _test_bof ENDP https://crocs.fi.muni.cz @CRoCS_MUNI GCC-fstack-protector-all 89 | PA193 - Secure coding Can an attacker still bypass stack canary? Example: Stack canary https://crocs.fi.muni.cz @CRoCS_MUNI How to bypass stack protection cookie? • Leak cookie value using information disclosure • Leak master cookie value • Write on the other direction in memory • Try cookie value blindly 90 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI How to bypass stack protection cookie? • Scenario: – long-term running of daemon on server – no exchange of cookie between calls 1. Obtain security cookie by one call – cookie is now known and can be incorporated into stack-smashing data 2. Use second call to change only the return address 91 | PA193 - Secure coding What attacker can do with changed return address? https://crocs.fi.muni.cz @CRoCS_MUNI SOURCE CODE PROTECTIONS COMPILER PROTECTIONS PLATFORM PROTECTIONS 92 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Data Execution Prevention (DEP) • Motto: When boundary between code and data blurs (buffer overflow, SQL injection…) then exploitation might be possible • Data Execution Prevention (DEP) – prevents application to execute code from non-executable memory region – available in modern operating systems • Linux > 2.6.8, WinXPSP2, Mac OSX, iOS, Android… – difference between ‘hardware’ and ‘software’ based DEP 93 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Hardware DEP • Supported from AMD64 and Intel Pentium 4 – OS must add support of this feature (around 2004) • CPU marks memory page as non-executable – most significant bit (63th) in page table entry (NX bit) – 0 == execute, 1 == data-only (non-executable) • Protection typically against buffer overflows • Cannot protect against all attacks! – e.g., code compiled at runtime (produced by JIT compiler) must have both instructions and data in executable page – attacker redirect execution to generated code (JIT spray) – used to bypass Adobe PDF and Flash security features • More in later lecture (Writing exploits) 94 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Software “DEP” • Unrelated to NX bit (no CPU support required) • When exception is raised, OS checks if exception handling routine pointer is in executable area – Microsoft’s Safe Structured Exception Handling • Software DEP is not preventing general execution in non-executable pages – different form of protection than hardware DEP 95 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Address Space Layout Randomization (ASLR) • Random reposition of executable base, stack, heap and libraries address in process’s address space – aim is to prevent exploit to reliably jump to required address • Performed every time a process is loaded into memory – random offset added to otherwise fixed address – applies to program and also dynamic libraries – entropy of random offset is important (bruteforce) • Operating System kernel ASLR (kASLR) – more problematic as long-running (random, but fixed until reboot) • Introduced by Memco software (1997) – fully implemented in Linux PaX patch (2001) – MS Vista, enabled by default (2007), MS Win 8 more entropy (2012) 96 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI ASLR – how much entropy? • Usually depends on available memory – possible attack combination with enforced low-memory situation • Linux PaX patch (2001) – around 24 bits entropy • MS Windows Vista (2007) – heap only around 5-7 bits entropy – stack 13-14 bits entropy – code 8 bits entropy – http://www.blackhat.com/presentations/bh-dc-07/Whitehouse/Presentation/bh-dc-07-Whitehouse.pdf • MS Windows 8 (2012) – additional entropy, Lagged Fibonacci Generator, registry keys, TPM, Time, ACPI, new rdrand CPU instruction – http://media.blackhat.com/bh-us- 12/Briefings/M_Miller/BH_US_12_Miller_Exploit_Mitigation_Slides.pdf 97 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI ASLR entropy in MS Windows 7&8 (2012) 98 | PA193 - Secure coding 𝑇𝑎𝑘𝑒𝑛 𝑓𝑟𝑜𝑚 Ken Johnson, Matt Miller (Microsoft Security Engineering Center), BlackHat USA 2012 ℎ𝑡𝑡𝑝://𝑚𝑒𝑑𝑖𝑎. 𝑏𝑙𝑎𝑐𝑘ℎ𝑎𝑡. 𝑐𝑜𝑚/𝑏ℎ − 𝑢𝑠 − 12/𝐵𝑟𝑖𝑒𝑓𝑖𝑛𝑔𝑠/𝑀_𝑀𝑖𝑙𝑙𝑒𝑟/𝐵𝐻_𝑈𝑆_12_𝑀𝑖𝑙𝑙𝑒𝑟_𝐸𝑥𝑝𝑙𝑜𝑖𝑡_𝑀𝑖𝑡𝑖𝑔𝑎𝑡𝑖𝑜𝑛_𝑆𝑙𝑖𝑑𝑒𝑠. 𝑝𝑑𝑓 https://crocs.fi.muni.cz @CRoCS_MUNI ASLR entropy in Linux systems (2017) 99 | PA193 - Secure coding Ganz, Peisert - ASLR, How Robust is the Randomness https://ieeexplore.ieee.org/abstract/document/8077804 https://crocs.fi.muni.cz @CRoCS_MUNI DEP&ASLR – MSVC compilation flags • /NXCOMPAT (on by default) – program is compatible with hardware DEP • /SAFESEH (on by default, only 32bit programs) • software DEP • /DYNAMICBASE (on by default) – basic ASLR – Property Pages → Configuration Properties → Linker → Advanced → Randomized Base Address – http://msdn.microsoft.com/en-us/library/bb384887.aspx • /HIGHENTROPYVA (on by default, only 64bit programs) – ASLR with higher entropy – http://msdn.microsoft.com/en-us/library/dn195771.aspx 100 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI ASLR – impact on attacks • ASLR introduced big shift in attacker mentality • Attacks are now based on gaps in ASLR – legacy programs/libraries/functions without ASLR support • ! /DYNAMICBASE – address space spraying (heap/JIT) – predictable memory regions, insufficient entropy 101 | PA193 - Secure coding Can attacker execute desired functionality without changing code? https://crocs.fi.muni.cz @CRoCS_MUNI Return-oriented programming (ROP) • Return-into-library technique (Solar Designer, 1997) – method for bypassing DEP – no write of attacker’s code to stack (as is prevented by DEP) 1. function return address replaced by pointer to standard library function 2. library function arguments replaced according to attackers needs 3. function return results in execution of library function and given arguments – Example: system call wrappers like system() • Borrowed code chunks – Problem: 64-bit hardware introduced different calling convention • first arguments to function passed in CPU registers instead of via stack – attacker tries to find instruction sequences from any function that pop values from the stack into registers (automated search by ROPgadget) – necessary arguments are inserted into registers – return-into-library attack is then executed as before 102 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Control flow integrity • Promising technique with low overhead • Classic CFI (2005), Modular CFI (2014) – avg 5% impact, 12% in worst case – part of LLVM C compiler (CFI usable for other languages as well) 1. Analysis of source code to establish control-flow graph (which function can call what other functions) 2. Assign shared labels between valid caller X and callee Y 3. When returning into function X, shared label is checked 4. Return to other function is not permitted More in later lecture (Return-oriented Programming) https://class.coursera.org/softwaresec-002/lecture/view?lecture_id=49 https://www.usenix.org/system/files/conference/usenixsecurity15/sec15-paper-carlini.pdf 103 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI DEP and ASLR should be combined • “For ASLR to be effective, DEP/NX must be enabled by default too.” M. Howard, Microsoft • /GS combined with /DYNAMICBASE and /NXCOMPAT – /NXCOMPAT (==DEP) – prevents insertion of new attacker's code and forces ROP – /DYNAMICBASE (==ASLR) randomizes code chunks utilized by ROP – /GS prevents modification of return pointer used later for ROP – /DYNAMICBASE randomizes position of master cookie for /GS • Visual Studio → Configuration properties → – Linker → All options – C/C++ → All options 104 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI SUMMARY 105 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Mandatory reading • SANS: 2017 State of Application Security – https://www.sans.org/reading-room/whitepapers/application/2017-state-application- security-balancing-speed-risk-38100 – Which applications are of main security concern? – What is expected time to deploy patch for critical security vulnerability? – How does your organization test applications for vulnerabilities? – Which language is the most common source of security risk? • Previous years are also worth of reading – https://www.sans.org/reading-room/whitepapers/application/ 106 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI107 | PA193 - Secure coding Questions #pa193_2022 https://crocs.fi.muni.cz @CRoCS_MUNI108 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Overview • Lecture: problems, prevention – buffer overflow (stack/heap/type) – string formatting problems – compiler protection – platform protections (DEP, ASLR) • Labs – compiler flags, buffer overflow exercises 109 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI PA193_01 - Language level vulnerabilities | PA193 - Secure coding110 https://crocs.fi.muni.cz @CRoCS_MUNI Final checklist 1. Be aware of possible problems and attacks – Don’t make exploitable errors at the first place! – Automated protections cannot fully defend everything 2. Use safer languages and safer versions of vulnerable functions – Secure C library (xxx_s functions) – Self-resizing strings/containers for C++ 3. Compile with all protection flags – MSVC: /RTC1,/DYNAMICBASE,/GS,/NXCOMPAT – GCC: -fstack-protector-all 4. Apply automated tools – BinScope Binary Analyzer, static and dynamic analyzers, vulns. scanners 5. Take advantage of protection in the modern OSes – and follow news in improvements in DEP, ASLR... 111 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Checkout • The most interesting thing learned today? 112 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI113 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI SoK: Eternal War in Memory 114 | PA193 - Secure coding http://www.cs.berkeley.edu/~dawnsong/papers/Oakland13-SoK-CR.pdf https://crocs.fi.muni.cz @CRoCS_MUNI SoK: Eternal War in Memory 115 | PA193 - Secure coding http://www.cs.berkeley.edu/~dawnsong/papers/Oakland13-SoK-CR.pdf https://crocs.fi.muni.cz @CRoCS_MUNI Coursera, Software Security • https://www.coursera.org/learn/software-security#syllabus 116 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Additional reading • Compiler Security Checks In Depth (MS) – http://msdn.microsoft.com/en-us/library/aa290051%28v=vs.71%29.aspx • GS cookie effectiveness (MS) – http://blogs.technet.com/b/srd/archive/2009/03/16/gs-cookie-protection- effectiveness-and-limitations.aspx • Design Your Program for Security – http://www.dwheeler.com/secure-programs/Secure-Programs-HOWTO/internals.html • Smashing The Stack For Fun And Profit – http://www-inst.cs.berkeley.edu/~cs161/fa08/papers/stack_smashing.pdf • Practical return-oriented programming – https://www.youtube.com/watch?v=AmyPzpeFN9k 117 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Books - optional • Writing secure code, chap. 5 • Security Development Lifecycle, chap. 11 • Embedded Systems Security, D., M. Kleidermacher 118 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Tutorials - optional • Buffer Overflow Exploitation Megaprimer (Linux) – http://www.securitytube.net/groups?operation=view&groupId=4 • Tenouk Buffer Overflow tutorial (Linux) – http://www.tenouk.com/Bufferoverflowc/bufferoverflowvulexploitdemo.html • Format string vulnerabilities primer (Linux) – http://www.securitytube.net/groups?operation=view&groupId=3 • Buffer overflow in Easy RM to MP3 utility (Windows) – https://www.corelan.be/index.php/2009/07/19/exploit-writing-tutorial-part-1-stack-based- overflows/ 119 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Heap overflow - references • Detailed explanation (Felix "FX" Lindner, 2006) – http://www.h-online.com/security/features/A-Heap-of-Risk-747161.html?view=print • Explanation in Phrack magazine (blackngel, 2009) – http://www.phrack.org/issues.html?issue=66&id=10#article • Defeating heap protection (Alexander Anisimov) – http://www.ptsecurity.com/download/defeating-xpsp2-heap-protection.pdf • Diehard – drop-in replacement for malloc with memory randomization – http://plasma.cs.umass.edu/emery/diehard.html – https://github.com/emeryberger/DieHard 120 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI ROP - references • Explanation of ROP – https://www.usenix.org/legacy/event/sec11/tech/full_papers/Schwartz.pdf • Blind ROP – Return-oriented programming without source code – http://www.scs.stanford.edu/brop/ • Automatic search for ROP gadgets – https://github.com/0vercl0k/rp 121 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI122 | PA193 - Secure coding 𝑇𝑎𝑘𝑒𝑛 𝑓𝑟𝑜𝑚 Ken Johnson, Matt Miller (Microsoft Security Engineering Center), BlackHat USA 2012 ℎ𝑡𝑡𝑝://𝑚𝑒𝑑𝑖𝑎. 𝑏𝑙𝑎𝑐𝑘ℎ𝑎𝑡. 𝑐𝑜𝑚/𝑏ℎ − 𝑢𝑠 − 12/𝐵𝑟𝑖𝑒𝑓𝑖𝑛𝑔𝑠/𝑀_𝑀𝑖𝑙𝑙𝑒𝑟/𝐵𝐻_𝑈𝑆_12_𝑀𝑖𝑙𝑙𝑒𝑟_𝐸𝑥𝑝𝑙𝑜𝑖𝑡_𝑀𝑖𝑡𝑖𝑔𝑎𝑡𝑖𝑜𝑛_𝑆𝑙𝑖𝑑𝑒𝑠. 𝑝𝑑𝑓 https://crocs.fi.muni.cz @CRoCS_MUNI Return-oriented programming (ROP) I. • Return-into-library technique (Solar Designer, 1997) – http://seclists.org/bugtraq/1997/Aug/63 – method for bypassing DEP – no write of attacker’s code to stack (as is prevented by DEP) 1. function return address is replaced by pointer of selected standard library function instead 2. library function arguments are also replaced according to attackers needs 3. function return will result in execution of library function with given arguments • Example: system call wrappers like system() 123 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Return-oriented programming (ROP) II. • But 64-bit hardware introduced different calling convention – first arguments to function are passed in CPU registers instead of via stack – harder to mount return-into-library attack • Borrowed code chunks – attacker tries to find instruction sequences from any function that pop values from the stack into registers – necessary arguments are inserted into registers – return-into-library attack is then executed as before • Return-oriented programming extends previous technique – multiple borrowed code chunks (gadgets) connected to execute Turingcomplete functionality (Shacham, 2007) – automated search for gadgets possible by ROPgadget – https://www.youtube.com/watch?v=a8_fDdWB2-M – partially defended by ASLR (but information leakage) 124 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI Blind ROP • Blind ROP technique (IEEE S&P 2015) – Randomization assumed – But no re-randomization on restart if server crash 1. Information leak for reading the stack 2. Find gadgets at runtime to affect write() 3. Dump binary to find gadgets (same as before) 125 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI126 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI127 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI How to detect and prevent problems? 1. Protection on the source code level – languages with/without implicit protection • containers/languages with array boundary checking – usage of safe alternatives to vulnerable function • vulnerable and safe functions for string manipulations – proper input checking 2. Protection by extensive testing (source code/binary/bytecode level) – automatic detection by static and dynamic checkers – code review, security testing 3. Protection by compiler (+ compiler flags) – runtime checks introduced by compiler (stack protection) 4. Protection by execution environment – DEP, ASLR, sandboxing, hardware isolation... 128 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI How to write code securely (w.r.t. BO) I. • Be aware of possibilities and principles • Use language providing (better) memory safety • Never trust user’s input, always check defensively • Use safe versions of string/memory functions • Always provide a format string argument • Use self-resizing strings (C++ std::string) • Use automatic bounds checking if possible – C++ std::vector.at(i)instead of vector[i] 129 | PA193 - Secure coding https://crocs.fi.muni.cz @CRoCS_MUNI How to write code securely (w.r.t. BO) II. • Run application with lowest possible privileges • Let your code to be reviewed • Use compiler-added protection • Use protection offered by platform (privileges, DEP, ASLR, sandboxing...) • Be responsible developer – your code can hurt other people 130 | PA193 - Secure coding