Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Go : Improvements to DSN Injection query #13644

Merged
merged 1 commit into from
Jul 19, 2023

Conversation

porcupineyhairs
Copy link
Contributor

This PR includes changes suggested in github/securitylab#748 (comment)

CC @JarLob

@github-actions
Copy link
Contributor

QHelp previews:

go/ql/src/experimental/CWE-74/DsnInjection.qhelp

SQL Data-source URI built from user-controlled sources

If a Data-Source Name (DSN) is built using untrusted user input without proper sanitization, the system may be vulnerable to DSN injection vulnerabilities.

Recommendation

If user input must be included in a DSN, additional steps should be taken to sanitize untrusted data, such as checking for special characters included in user input.

Example

In the following examples, the code accepts the db name from the user, which it then uses to build a DSN string.

The following example uses the unsanitized user input directly in the process of constructing a DSN name. A malicious user could provide special characters to change the meaning of this string, and carry out unexpected database operations.

func bad() interface{} {
	name := os.Args[1:]
	// This is bad. `name` can be something like `test?allowAllFiles=true&` which will allow an attacker to access local files.
	dbDSN := fmt.Sprintf("%s:%s@tcp(%s:%d)/%s?charset=utf8", "username", "password", "127.0.0.1", 3306, name)
	db, _ := sql.Open("mysql", dbDSN)
	return db
}

In the following example, the input provided by the user is sanitized before it is included in the DSN string. This ensures the meaning of the DSN string cannot be changed by a malicious user.

func good() (interface{}, error) {
	name := os.Args[1]
	hasBadChar, _ := regexp.MatchString(".*[?].*", name)

	if hasBadChar {
		return nil, errors.New("Bad input")
	}

	dbDSN := fmt.Sprintf("%s:%s@tcp(%s:%d)/%s?charset=utf8", "username", "password", "127.0.0.1", 3306, name)
	db, _ := sql.Open("mysql", dbDSN)
	return db, nil
}

References

@owen-mc owen-mc merged commit 5b0d4ce into github:main Jul 19, 2023
8 checks passed
@porcupineyhairs porcupineyhairs deleted the dsnImprove branch July 19, 2023 16:50
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants