Day 1 of 3 - Focus: Security principles, SDLC integration, and defensive coding
Before diving into advanced security concepts, let's review the foundational technologies that secure software architecture builds upon.
HTTP (HyperText Transfer Protocol): Basic web communication protocol that sends data in plain text.
HTTPS (HTTP Secure): Encrypted version of HTTP that protects data during transmission.
Simple Explanation: HTTP is like sending a postcard - anyone can read your message. HTTPS is like sending a letter in a sealed, tamper-proof envelope.
📬 Analogy: HTTP = shouting your credit card number across a crowded room. HTTPS = whispering it directly into the cashier's ear in a private booth.
Definition: Set of rules and protocols that allow different software applications to communicate with each other.
Purpose: Enable applications to request and share data or functionality without knowing internal implementation details.
Simple Explanation: APIs are like waiters in a restaurant - they take your order, communicate with the kitchen, and bring back exactly what you requested.
🍽️ Analogy: You (the app) tell the waiter (API) what you want from the menu. The waiter takes your request to the kitchen (another app/database), and brings back your food (data) without you needing to know how the kitchen works.
Database: Organized collection of data stored electronically, typically managed by a Database Management System (DBMS).
SQL: Structured Query Language used to communicate with relational databases.
Simple Explanation: A database is like a smart filing cabinet that can quickly find, sort, and organize any information you need.
🗂️ Analogy: Database = massive library with a super-efficient librarian (SQL) who can instantly find any book you ask for using specific request phrases.
Client: Device or application that requests services (e.g., your web browser, mobile app).
Server: Computer system that provides services or resources to clients over a network.
Simple Explanation: Clients ask for things, servers provide them. Like customers and shopkeepers, but for computer programs.
🏪 Analogy: Client = customer walking into a restaurant. Server = kitchen that prepares and serves your order. You don't need to know how the kitchen works, just how to place your order.
Encryption: Converting data into a coded format that can be decoded back to original form with the right key.
Hashing: Converting data into a fixed-size string that cannot be reversed to get the original data.
Simple Explanation: Encryption is reversible protection, hashing is permanent transformation for verification.
🔐 Analogy: Encryption = locking your diary with a key (you can unlock it later). Hashing = shredding a document to create a unique fingerprint (you can't recreate the original, but you can verify if two documents match).
Session: Temporary period when a user interacts with a web application, maintaining state across multiple requests.
Cookies: Small pieces of data stored by the web browser to remember information about the user.
Simple Explanation: Sessions track your current visit, cookies remember you for future visits.
🎫 Analogy: Session = temporary wristband at an amusement park (tracks your current visit). Cookie = loyalty card that remembers your preferences for next time you visit.
Understanding the fundamental principles that guide secure software development is essential for the HSC exam.
Ensuring that sensitive information is accessible only to authorized individuals. Achieved through encryption, access controls, and data classification.
Maintaining the accuracy and reliability of data throughout its lifecycle. Protected through checksums, digital signatures, and version controls.
Ensuring that systems and data are accessible when needed. Maintained through redundancy, backups, and disaster recovery plans.
Verifying the identity of users or systems. Implemented through passwords, biometrics, multi-factor authentication, and digital certificates.
Controlling what authenticated users can access and do. Managed through role-based access control (RBAC) and permission systems.
Tracking and logging user actions to maintain responsibility. Achieved through audit trails, logging systems, and monitoring.
Memory Aid: "Can I Access?"
Confidentiality + Integrity + Availability = Complete Security
Security must be integrated into every phase of software development, not added as an afterthought.
What this means: Before building anything, decide what security features are needed and what threats to protect against.
🏗️ Analogy: Like planning security for a new house - deciding where to put locks, alarms, and cameras before you start building.
What this means: Create detailed blueprints showing how security will be built into the system's structure and components.
📐 Analogy: Like an architect drawing detailed security plans - showing exactly where each lock, security door, and safe room will go.
What this means: Write code that follows security best practices, validate all inputs, and have other programmers check your work.
🔨 Analogy: Like building the house with quality materials and having inspectors check each step to ensure it's done safely.
What this means: Test how different parts of the system work together securely, especially when they communicate with each other.
🔗 Analogy: Like testing that all the security systems (alarms, cameras, locks) work together and can communicate properly.
What this means: Thoroughly test the system for security holes using automated tools and simulated attacks to find weaknesses.
🔍 Analogy: Like hiring professional burglars to try breaking into your house to find any weak spots you missed.
What this means: Set up the system in the real environment with proper security settings, user permissions, and server configurations.
🏠 Analogy: Like moving into your new house and setting up all the security codes, giving keys to the right people, and activating all alarms.
What this means: Keep the system secure over time by applying security updates, monitoring for threats, and fixing new vulnerabilities as they're discovered.
🔧 Analogy: Like regularly maintaining your house security - updating alarm codes, fixing broken locks, and watching for new security threats in your neighborhood.
Understanding common security vulnerabilities is crucial for developing secure software.
Description: Malicious scripts injected into web applications that execute in users' browsers.
Prevention: Input validation, output encoding, Content Security Policy (CSP)
What this means: Attackers trick a website into running their malicious code in other users' browsers, potentially stealing their data.
🎭 Analogy: Like a malicious actor sneaking onto a theater stage and convincing the audience they're part of the show, then stealing their wallets while they're distracted.
Description: Unauthorized commands transmitted from a user that the application trusts.
Prevention: CSRF tokens, SameSite cookies, origin validation
What this means: Attackers trick users into performing actions they didn't intend to do on websites where they're already logged in.
📧 Analogy: Like someone forging your signature on a check while you're not looking, using your trusted relationship with the bank to steal money.
Description: Malicious SQL code inserted into application queries.
Prevention: Parameterized queries, input validation, least privilege access
What this means: Attackers insert malicious database commands into user input fields, potentially accessing or destroying sensitive data.
🗃️ Analogy: Like sneaking extra instructions into a filing cabinet request - instead of "get me file A", the request becomes "get me file A AND give me access to ALL secret files".
Description: Timing-dependent bugs where multiple processes access shared resources.
Prevention: Proper synchronization (locks, semaphores), atomic operations, thread safety mechanisms
What this means: Multiple parts of a program try to use the same resource at the same time, causing unpredictable and potentially dangerous results. Prevented using locks, semaphores, or atomic operations.
🏃♂️ Analogy: Like two people trying to withdraw the last $100 from a bank account at the exact same time - both might get the money, overdrawing the account. The solution is like having a "one customer at a time" rule.
Input Validation: Verify that input meets expected format, type, and range
Input Sanitization: Remove or escape potentially harmful characters
Error Handling: Provide meaningful error messages without revealing sensitive information
Key Principle: Every input must pass ALL validation checks. Any failure = immediate rejection.
Proper memory allocation and deallocation to prevent buffer overflows and memory leaks.
Secure session creation, maintenance, and destruction with proper timeout and encryption.
Proper exception handling that doesn't expose system information to attackers.
Analyzes source code for security vulnerabilities without executing the program.
What this means: Automated tools examine the written code (like reading a recipe) to spot potential security problems before the program runs.
📝 Analogy: Like a spell-checker for code - it reads through your writing to find mistakes without actually running the program, just like spell-check finds errors without reading your essay aloud.
Tests running applications for security vulnerabilities by simulating attacks.
What this means: Tools test the live, running application by trying different attacks to see what actually works against the real system.
🎮 Analogy: Like testing a video game by actually playing it and trying to break it - you interact with the finished product to find bugs, rather than just reading the code.
Systematic review of security weaknesses in applications and infrastructure.
What this means: A comprehensive examination of all system components to identify and catalog every potential security weakness, like a security audit.
🏠 Analogy: Like a home security inspection - systematically checking every door, window, and lock to create a complete list of what needs to be fixed or improved.
Simulated cyber attacks to identify exploitable vulnerabilities.
What this means: Ethical hackers try to actually break into the system using real attack techniques to prove which vulnerabilities can be exploited.
🕵️ Analogy: Like hiring ethical security consultants to test your house security - they use real techniques to find weaknesses and help you improve protection, working with your permission to make your home safer.
Building security into the software architecture from the beginning, rather than adding it later.
Symmetric Encryption: Same key used for encryption and decryption (faster, used for large data)
Asymmetric Encryption: Different keys for encryption and decryption (more secure, used for key exchange)
Digital Signatures: Use asymmetric cryptography to verify data integrity and authenticity
Key Management: Secure storage, distribution, and rotation of encryption keys
Isolated execution environments that restrict code access to system resources, preventing malicious code from affecting the broader system.
Safeguarding sensitive information from unauthorized access, modification, or destruction through encryption and access controls.
Reducing attack surface through defensive coding, regular updates, and proactive vulnerability management.
Meeting legal requirements for data protection (GDPR, Privacy Act) and industry standards (ISO 27001, PCI DSS).
End User Capabilities: Security design must consider user technical skills, accessibility needs, and usage patterns. Simple interfaces reduce security errors, while clear communication helps users make secure choices.
Defense in Depth Principle: No single security measure is perfect. Multiple overlapping layers provide comprehensive protection.
Firewalls, routers, network segmentation
DMZ, web proxies, load balancers
Authentication, input validation, HTTPS
Encryption, access controls, backups
Authentication: API keys, OAuth tokens, JWT validation
Rate Limiting: Prevent abuse through request throttling
Input Validation: Strict data type and format checking
HTTPS Only: Encrypted communication channels
Issues: Weak passwords, session fixation, improper logout
Prevention: Strong authentication, secure session handling, proper timeouts
What this means: The system fails to properly verify who users are or manage their login sessions, allowing unauthorized access.
🗝️ Analogy: Like a hotel giving out master keys that never expire, or not checking IDs properly - anyone could pretend to be a guest and access any room.
Issues: Unvalidated redirects leading to malicious sites
Prevention: Validate redirect URLs, use allowlists for trusted destinations
What this means: Websites automatically redirect users to external sites without checking if those sites are safe, potentially sending users to malicious websites.
🚶♂️ Analogy: Like following GPS directions that send you to a dangerous neighborhood instead of your intended destination - you trusted the redirect but ended up somewhere harmful.
File Attacks: Malicious file uploads, path traversal
Side Channel: Information leakage through timing, power consumption
Prevention: File validation, secure file storage, consistent response times
What this means: File Attacks: Attackers upload malicious files or access restricted directories. Side Channel: Attackers gain information by analyzing system behavior patterns.
📁 Analogy: File attacks are like smuggling weapons in a gift box, while side channel attacks are like a spy timing how long it takes guards to check different doors to figure out which one leads to the vault.
Reducing attack surface by disabling unnecessary services, applying security patches, and configuring secure defaults.
Incident response plans, containment strategies, evidence preservation, and stakeholder communication.
Maintaining operations during security incidents through backup systems, redundancy, and recovery procedures.
Systematic approach to restore systems and data after security breaches or system failures.
Automation may reduce some jobs but creates new cybersecurity roles. Need for retraining and skill development.
Balancing functionality with user privacy rights. Transparent data collection and use policies.
Protecting software copyrights while respecting open-source licenses and avoiding patent infringement.
Security considerations in emerging technologies affecting traditional business models and social structures.
Test your knowledge with practice questions and interactive quizzes
Test your understanding with these HSC-style questions (85% Year 12, 15% Year 11 content)
Compare and contrast SAST and DAST security testing methods. Discuss the advantages and disadvantages of each approach and explain when each would be most appropriate in the SDLC. (6 marks)
Explain the three core principles of Privacy by Design and provide a practical example of how each principle would be implemented in a web application that collects user data. (6 marks)
A web application is vulnerable to SQL injection attacks. Describe three different methods that could be used to prevent this vulnerability and explain how each method works. (6 marks)
Describe how security considerations should be integrated into the Requirements Definition and Design phases of the SDLC. Include specific activities and deliverables for each phase. (8 marks)
Distinguish between authentication and authorization in software security. Provide two specific examples of each and explain how they work together to protect a system. (6 marks)
Analyze the benefits to an enterprise of implementing safe and secure development practices. Discuss at least four different areas of impact. (8 marks)
Explain how proper use of data types in programming can contribute to software security. Provide an example of a security issue that could arise from improper data type handling. (4 marks)
Describe how algorithm efficiency relates to security in software applications. Explain one way that inefficient algorithms could create security vulnerabilities. (4 marks)
Explain the concept of "Defense in Depth" and provide three specific examples of how different security layers would protect against a web application attack. Discuss why relying on a single security measure is insufficient. (8 marks)
A software development team wants to implement security throughout their SDLC. Describe specific security activities that should occur in the Development and Testing phases, and explain why security cannot be effectively added only at the end of the project. (6 marks)
Compare XSS and CSRF vulnerabilities. Explain how each attack works, provide a real-world scenario for each, and describe one prevention method for each vulnerability. (8 marks)
A company needs to implement a comprehensive security testing program. Explain the differences between SAST and DAST, when each should be used in the SDLC, and why both are necessary for effective security testing. (6 marks)
Explain how the three core principles of Privacy by Design can be implemented in a social media application. For each principle, provide a specific technical implementation example. (6 marks)
Analyze how implementing secure software development practices benefits an organization. Discuss impacts on productivity, costs, and business continuity. Provide specific examples for each area. (8 marks)
Explain why input validation is important in software security. Describe two different types of input validation and provide an example of each. (4 marks)
Describe how proper error handling contributes to software security. Explain what information should and should not be included in error messages shown to users. (4 marks)
A company is developing a new e-commerce platform. Explain how security considerations should influence the choice of development methodology (Waterfall vs Agile). Discuss the security advantages and challenges of each approach. (6 marks)
Practice identifying and fixing security vulnerabilities in real code
Examine the following Java code used for user login:
public boolean authenticateUser(String username, String password) {
String query = "SELECT * FROM users WHERE username = '" + username +
"' AND password = '" + password + "'";
// Execute query and check if user exists
ResultSet rs = stmt.executeQuery(query);
return rs.next();
}
Part A: Identify the security vulnerabilities in this code and explain how an attacker could exploit them. (4 marks)
Part B: Rewrite this code to eliminate the security vulnerabilities. (4 marks)
Part C: Explain why your solution is more secure than the original code. (2 marks)
public boolean authenticateUser(String username, String password) {
// Input validation
if (username == null || password == null ||
username.length() > 50 || password.length() > 100) {
return false;
}
// Parameterized query
String query = "SELECT password_hash FROM users WHERE username = ?";
PreparedStatement pstmt = connection.prepareStatement(query);
pstmt.setString(1, username);
ResultSet rs = pstmt.executeQuery();
if (rs.next()) {
String storedHash = rs.getString("password_hash");
return BCrypt.checkpw(password, storedHash);
}
return false;
}
Review this Python function for searching products in an e-commerce system:
def search_products(category, min_price, max_price):
query = f"SELECT * FROM products WHERE category = '{category}' "
query += f"AND price BETWEEN {min_price} AND {max_price}"
cursor.execute(query)
return cursor.fetchall()
Part A: What security vulnerabilities exist in this code? Provide a specific example of how an attacker could exploit one vulnerability. (4 marks)
Part B: Write a secure version of this function. (4 marks)
def search_products(category, min_price, max_price):
# Input validation
if not category or len(category) > 50:
raise ValueError("Invalid category")
try:
min_price = float(min_price)
max_price = float(max_price)
if min_price < 0 or max_price < min_price:
raise ValueError("Invalid price range")
except ValueError:
raise ValueError("Invalid price format")
# Parameterized query
query = "SELECT * FROM products WHERE category = ? AND price BETWEEN ? AND ?"
cursor.execute(query, (category, min_price, max_price))
return cursor.fetchall()
A web application displays user comments using this PHP code:
<?php
function displayComments($comments) {
foreach ($comments as $comment) {
echo "<div class='comment'>";
echo "<h4>" . $comment['username'] . "</h4>";
echo "<p>" . $comment['message'] . "</p>";
echo "</div>";
}
}
?>
Part A: Identify the XSS vulnerability and explain how an attacker could exploit it. Provide a specific malicious input example. (4 marks)
Part B: Rewrite the code to prevent XSS attacks. (3 marks)
Part C: Explain one additional security measure that could be implemented to further protect against XSS. (3 marks)
<?php
function displayComments($comments) {
foreach ($comments as $comment) {
// Input validation
if (empty($comment['username']) || empty($comment['message'])) {
continue;
}
echo "<div class='comment'>";
// HTML encode output to prevent XSS
echo "<h4>" . htmlspecialchars($comment['username'], ENT_QUOTES, 'UTF-8') . "</h4>";
echo "<p>" . htmlspecialchars($comment['message'], ENT_QUOTES, 'UTF-8') . "</p>";
echo "</div>";
}
}
?>
Review this JavaScript function that processes user registration:
function registerUser(email, password, age) {
// Basic email check
if (email.includes('@')) {
// Save user to database
const user = {
email: email,
password: password,
age: age
};
database.save(user);
return "Registration successful";
} else {
return "Invalid email";
}
}
Part A: List at least 4 security issues with this input validation. (4 marks)
Part B: Write an improved version with proper input validation. (6 marks)
function registerUser(email, password, age) {
// Email validation with proper regex
const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
if (!emailRegex.test(email) || email.length > 100) {
return "Invalid email format";
}
// Password validation
if (password.length < 8 || password.length > 128) {
return "Password must be 8-128 characters";
}
const passwordRegex = /^(?=.*[a-z])(?=.*[A-Z])(?=.*\d)(?=.*[@$!%*?&])[A-Za-z\d@$!%*?&]/;
if (!passwordRegex.test(password)) {
return "Password must contain uppercase, lowercase, number, and special character";
}
// Age validation
const ageNum = parseInt(age);
if (isNaN(ageNum) || ageNum < 13 || ageNum > 120) {
return "Age must be between 13 and 120";
}
// Hash password before storage
const hashedPassword = await bcrypt.hash(password, 12);
const user = {
email: email.toLowerCase().trim(),
password: hashedPassword,
age: ageNum
};
database.save(user);
return "Registration successful";
}
Scenario: A login system stores passwords in plain text and has weak authentication logic. Identify the vulnerabilities and provide secure alternatives.
<?php
// Insecure authentication system
function login($username, $password) {
$conn = new mysqli("localhost", "user", "pass", "db");
// Plain text password storage and SQL injection vulnerability
$query = "SELECT * FROM users WHERE username = '$username' AND password = '$password'";
$result = $conn->query($query);
if ($result->num_rows > 0) {
// Weak session management
$_SESSION['user'] = $username;
$_SESSION['logged_in'] = true;
return true;
}
return false;
}
// No password complexity requirements
function register($username, $password) {
$conn = new mysqli("localhost", "user", "pass", "db");
// Storing plain text password
$query = "INSERT INTO users (username, password) VALUES ('$username', '$password')";
$conn->query($query);
}
?>
Part A: Identify at least 5 security vulnerabilities in this authentication system. (5 marks)
Part B: Rewrite the code with secure authentication practices. (5 marks)
<?php
// Secure authentication system
function login($username, $password) {
$conn = new mysqli("localhost", "user", "pass", "db");
// Use prepared statements to prevent SQL injection
$stmt = $conn->prepare("SELECT id, username, password_hash, failed_attempts, last_attempt FROM users WHERE username = ?");
$stmt->bind_param("s", $username);
$stmt->execute();
$result = $stmt->get_result();
if ($result->num_rows === 1) {
$user = $result->fetch_assoc();
// Check for account lockout (rate limiting)
if ($user['failed_attempts'] >= 5 && time() - strtotime($user['last_attempt']) < 300) {
throw new Exception('Account temporarily locked due to too many failed attempts');
}
// Verify password using secure hashing
if (password_verify($password, $user['password_hash'])) {
// Reset failed attempts on successful login
$stmt = $conn->prepare("UPDATE users SET failed_attempts = 0 WHERE id = ?");
$stmt->bind_param("i", $user['id']);
$stmt->execute();
// Secure session management
session_regenerate_id(true); // Prevent session fixation
$_SESSION['user_id'] = $user['id'];
$_SESSION['username'] = $user['username'];
$_SESSION['logged_in'] = true;
$_SESSION['login_time'] = time();
return true;
} else {
// Increment failed attempts
$stmt = $conn->prepare("UPDATE users SET failed_attempts = failed_attempts + 1, last_attempt = NOW() WHERE id = ?");
$stmt->bind_param("i", $user['id']);
$stmt->execute();
}
}
// Generic error message to prevent username enumeration
throw new Exception('Invalid username or password');
}
function register($username, $password) {
// Password complexity validation
if (strlen($password) < 8) {
throw new Exception('Password must be at least 8 characters long');
}
if (!preg_match('/^(?=.*[a-z])(?=.*[A-Z])(?=.*\d)(?=.*[@$!%*?&])[A-Za-z\d@$!%*?&]/', $password)) {
throw new Exception('Password must contain uppercase, lowercase, number, and special character');
}
$conn = new mysqli("localhost", "user", "pass", "db");
// Check if username already exists
$stmt = $conn->prepare("SELECT id FROM users WHERE username = ?");
$stmt->bind_param("s", $username);
$stmt->execute();
if ($stmt->get_result()->num_rows > 0) {
throw new Exception('Username already exists');
}
// Hash password securely
$password_hash = password_hash($password, PASSWORD_ARGON2ID);
// Use prepared statement for secure insertion
$stmt = $conn->prepare("INSERT INTO users (username, password_hash, created_at) VALUES (?, ?, NOW())");
$stmt->bind_param("ss", $username, $password_hash);
$stmt->execute();
}
?>
Scenario: A web application has an admin panel with weak authorization checks. Find the vulnerability that allows privilege escalation.
<?php
// Weak authorization implementation
function checkAdmin() {
// Only checks if user is logged in, not their role
if (!isset($_SESSION['logged_in']) || !$_SESSION['logged_in']) {
header('Location: login.php');
exit();
}
return true;
}
// Admin panel access
if (checkAdmin()) {
echo "<h1>Admin Panel</h1>";
// Dangerous: Any logged-in user can access admin functions
if ($_POST['action'] === 'delete_user') {
$user_id = $_POST['user_id'];
$query = "DELETE FROM users WHERE id = $user_id";
mysqli_query($conn, $query);
echo "User deleted successfully";
}
if ($_POST['action'] === 'promote_user') {
$user_id = $_POST['user_id'];
// Direct database manipulation without proper authorization
$query = "UPDATE users SET role = 'admin' WHERE id = $user_id";
mysqli_query($conn, $query);
}
}
?>
Part A: Identify the authorization bypass vulnerability and explain how it can be exploited. (4 marks)
Part B: Rewrite the code with proper role-based access control. (6 marks)
<?php
// Proper role-based authorization
function checkAdminAccess() {
// Check if user is logged in
if (!isset($_SESSION['user_id']) || !$_SESSION['logged_in']) {
http_response_code(401);
header('Location: login.php');
exit();
}
// Verify user's role from database
$conn = new mysqli("localhost", "user", "pass", "db");
$stmt = $conn->prepare("SELECT role FROM users WHERE id = ?");
$stmt->bind_param("i", $_SESSION['user_id']);
$stmt->execute();
$result = $stmt->get_result();
if ($result->num_rows !== 1) {
http_response_code(401);
header('Location: login.php');
exit();
}
$user = $result->fetch_assoc();
if ($user['role'] !== 'admin') {
http_response_code(403);
die('Access denied: Admin privileges required');
}
return true;
}
// Secure admin functions with proper authorization
if (checkAdminAccess()) {
echo "<h1>Admin Panel</h1>";
if ($_POST['action'] === 'delete_user') {
// Validate and sanitize input
$user_id = filter_var($_POST['user_id'], FILTER_VALIDATE_INT);
if (!$user_id) {
die('Invalid user ID');
}
// Prevent self-deletion
if ($user_id == $_SESSION['user_id']) {
die('Cannot delete your own account');
}
// Use prepared statement
$stmt = $conn->prepare("DELETE FROM users WHERE id = ? AND role != 'admin'");
$stmt->bind_param("i", $user_id);
if ($stmt->execute() && $stmt->affected_rows > 0) {
// Log admin action for audit trail
logAdminAction($_SESSION['user_id'], "delete_user", $user_id);
echo "User deleted successfully";
} else {
echo "Failed to delete user or user is an admin";
}
}
}
function logAdminAction($admin_id, $action, $target_id) {
$conn = new mysqli("localhost", "user", "pass", "db");
$stmt = $conn->prepare("INSERT INTO admin_logs (admin_id, action, target_id, timestamp, ip_address) VALUES (?, ?, ?, NOW(), ?)");
$ip = $_SERVER['REMOTE_ADDR'];
$stmt->bind_param("isis", $admin_id, $action, $target_id, $ip);
$stmt->execute();
}
?>
Scenario: A banking application processes money transfers but lacks proper session management and CSRF protection. Analyze the security risks.
<?php
// Vulnerable money transfer system
session_start();
// No CSRF protection
if ($_POST['transfer']) {
$amount = $_POST['amount'];
$to_account = $_POST['to_account'];
$from_account = $_SESSION['account_id'];
// No session timeout or validation
if (isset($_SESSION['logged_in'])) {
// Direct database update without additional verification
$query = "UPDATE accounts SET balance = balance - $amount WHERE id = $from_account";
mysqli_query($conn, $query);
$query = "UPDATE accounts SET balance = balance + $amount WHERE id = $to_account";
mysqli_query($conn, $query);
echo "Transfer of $$amount completed";
}
}
?>
<form method="POST">
<input type="hidden" name="transfer" value="1">
<input type="text" name="to_account" placeholder="Recipient Account">
<input type="number" name="amount" placeholder="Amount">
<button type="submit">Transfer Money</button>
</form>
Part A: Identify at least 6 security vulnerabilities in this money transfer system. (6 marks)
Part B: Rewrite the code with secure session management and CSRF protection. (4 marks)
<?php
// Secure money transfer with CSRF protection
session_start();
// Generate CSRF token if not exists
if (!isset($_SESSION['csrf_token'])) {
$_SESSION['csrf_token'] = bin2hex(random_bytes(32));
}
// Set session timeout (30 minutes)
if (isset($_SESSION['last_activity']) && (time() - $_SESSION['last_activity'] > 1800)) {
session_unset();
session_destroy();
header('Location: login.php');
exit();
}
$_SESSION['last_activity'] = time();
if ($_POST['transfer']) {
// Verify CSRF token
if (!hash_equals($_SESSION['csrf_token'], $_POST['csrf_token'])) {
http_response_code(403);
die('CSRF token validation failed');
}
// Validate session and user authentication
if (!isset($_SESSION['logged_in']) || !$_SESSION['logged_in'] || !isset($_SESSION['user_id'])) {
http_response_code(401);
header('Location: login.php');
exit();
}
// Validate and sanitize inputs
$amount = filter_var($_POST['amount'], FILTER_VALIDATE_FLOAT);
$to_account = filter_var($_POST['to_account'], FILTER_VALIDATE_INT);
if (!$amount || $amount <= 0 || $amount > 10000) {
die('Invalid transfer amount');
}
if (!$to_account) {
die('Invalid recipient account');
}
// Get user's account info with balance verification
$stmt = $conn->prepare("SELECT id, balance FROM accounts WHERE user_id = ?");
$stmt->bind_param("i", $_SESSION['user_id']);
$stmt->execute();
$result = $stmt->get_result();
if ($result->num_rows !== 1) {
die('Account not found');
}
$account = $result->fetch_assoc();
// Check sufficient balance
if ($account['balance'] < $amount) {
die('Insufficient funds');
}
// Verify recipient account exists
$stmt = $conn->prepare("SELECT id FROM accounts WHERE id = ?");
$stmt->bind_param("i", $to_account);
$stmt->execute();
if ($stmt->get_result()->num_rows !== 1) {
die('Recipient account not found');
}
// Use database transaction for atomic operation
$conn->begin_transaction();
try {
// Debit from sender
$stmt = $conn->prepare("UPDATE accounts SET balance = balance - ? WHERE id = ? AND balance >= ?");
$stmt->bind_param("ddi", $amount, $account['id'], $amount);
$stmt->execute();
if ($stmt->affected_rows !== 1) {
throw new Exception('Transfer failed - insufficient funds');
}
// Credit to recipient
$stmt = $conn->prepare("UPDATE accounts SET balance = balance + ? WHERE id = ?");
$stmt->bind_param("di", $amount, $to_account);
$stmt->execute();
// Log transaction
$stmt = $conn->prepare("INSERT INTO transactions (from_account, to_account, amount, timestamp, session_id) VALUES (?, ?, ?, NOW(), ?)");
$stmt->bind_param("iids", $account['id'], $to_account, $amount, session_id());
$stmt->execute();
$conn->commit();
// Regenerate CSRF token after successful operation
$_SESSION['csrf_token'] = bin2hex(random_bytes(32));
echo "Transfer of $$amount completed successfully";
} catch (Exception $e) {
$conn->rollback();
die('Transfer failed: ' . $e->getMessage());
}
}
?>
<form method="POST">
<input type="hidden" name="transfer" value="1">
<input type="hidden" name="csrf_token" value="<?php echo $_SESSION['csrf_token']; ?>">
<input type="text" name="to_account" placeholder="Recipient Account" required>
<input type="number" name="amount" placeholder="Amount" min="1" max="10000" step="0.01" required>
<button type="submit">Transfer Money</button>
</form>
Test your understanding with this comprehensive quiz covering all security topics!