Summary
A security audit identified 12 vulnerabilities (4 Critical, 5 High, 2 Medium, 1 Low) including unauthenticated data access, multiple SQL injection vectors, and globally disabled CSRF protection.
Critical Findings
1. Search Controller — Authentication Commented Out (CRITICAL)
application/controllers/Search.php:19:
//$this->gen->checklogin(); // COMMENTED OUT!
The only protection is ajaxOnly() (trivially bypassed with X-Requested-With: XMLHttpRequest header). Any unauthenticated user can:
GET /search/itemSearch?v= — enumerate all items (names, codes, prices, quantities)
GET /search/transSearch?v= — enumerate all transactions (amounts, customer names/phones/emails, payment methods)
2. SQL Injection — ORDER BY/LIMIT (CRITICAL)
application/models/Transaction.php:42-43 — $orderBy, $orderFormat, $limit, $start from GET params interpolated directly into raw SQL (SQLite3 branch):
$q = "SELECT ... ORDER BY {$orderBy} {$orderFormat} LIMIT {$limit} OFFSET {$start}";
3. SQL Injection — Date Range Report (CRITICAL)
application/models/Transaction.php:306 — $from_date, $to_date from URL segments:
WHERE date(transactions.transDate) >= {$from_date} AND date(transactions.transDate) <= {$to_date}
4. SQL Injection — Year Earnings Graph (HIGH)
application/models/Genmod.php:192 — $year from URL segment:
WHERE strftime('%Y', transDate) = '{$year_to_fetch}'
5. CSRF Protection Disabled Globally (HIGH)
application/config/config.php:457:
$config['csrf_protection'] = FALSE;
6. Test Controller — Unauthenticated (HIGH)
application/controllers/Test.php — No auth, outputs bcrypt hash of "123456" (revealing default password pattern) and MD5 of server timestamp.
Recommended Fixes
- Uncomment
checkLogin() in Search controller
- Parameterize ALL SQL queries — use
? placeholders for all user input
- Enable CSRF protection (
$config['csrf_protection'] = TRUE)
- Remove or protect Test controller in production
- Whitelist ORDER BY column names rather than accepting raw user input
Disclosure
Filed in good faith. No exploit code provided.
Summary
A security audit identified 12 vulnerabilities (4 Critical, 5 High, 2 Medium, 1 Low) including unauthenticated data access, multiple SQL injection vectors, and globally disabled CSRF protection.
Critical Findings
1. Search Controller — Authentication Commented Out (CRITICAL)
application/controllers/Search.php:19://$this->gen->checklogin(); // COMMENTED OUT!The only protection is
ajaxOnly()(trivially bypassed withX-Requested-With: XMLHttpRequestheader). Any unauthenticated user can:GET /search/itemSearch?v=— enumerate all items (names, codes, prices, quantities)GET /search/transSearch?v=— enumerate all transactions (amounts, customer names/phones/emails, payment methods)2. SQL Injection — ORDER BY/LIMIT (CRITICAL)
application/models/Transaction.php:42-43—$orderBy,$orderFormat,$limit,$startfrom GET params interpolated directly into raw SQL (SQLite3 branch):3. SQL Injection — Date Range Report (CRITICAL)
application/models/Transaction.php:306—$from_date,$to_datefrom URL segments:4. SQL Injection — Year Earnings Graph (HIGH)
application/models/Genmod.php:192—$yearfrom URL segment:5. CSRF Protection Disabled Globally (HIGH)
application/config/config.php:457:6. Test Controller — Unauthenticated (HIGH)
application/controllers/Test.php— No auth, outputs bcrypt hash of "123456" (revealing default password pattern) and MD5 of server timestamp.Recommended Fixes
checkLogin()in Search controller?placeholders for all user input$config['csrf_protection'] = TRUE)Disclosure
Filed in good faith. No exploit code provided.