Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Sources/Fuzzilli/Execution/REPRL.swift
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ public class REPRL: ComponentBase, ScriptRunner {
private let maxExecsBeforeRespawn = 1000

/// Commandline arguments for the executable
private let processArguments: [String]
public private(set) var processArguments: [String]

/// Environment variables for the child process
private var env = [String]()
Expand Down
2 changes: 2 additions & 0 deletions Sources/Fuzzilli/Execution/ScriptRunner.swift
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@
// limitations under the License.

public protocol ScriptRunner: Component {
var processArguments: [String] { get }

/// Executes a script, waits for it to complete, and returns the result.
func run(_ script: String, withTimeout timeout: UInt32) -> Execution

Expand Down
1 change: 1 addition & 0 deletions Sources/Fuzzilli/Fuzzer.swift
Original file line number Diff line number Diff line change
Expand Up @@ -646,6 +646,7 @@ public class Fuzzer {
program.comments.add("TERMSIG: \(termsig)\n", at: .footer)
program.comments.add("STDERR:\n" + stderr, at: .footer)
program.comments.add("STDOUT:\n" + stdout, at: .footer)
program.comments.add("ARGS: \(runner.processArguments.joined(separator: " "))\n", at: .footer)
}
Assert(program.comments.at(.footer)?.contains("CRASH INFO") ?? false)

Expand Down
2 changes: 2 additions & 0 deletions Sources/Fuzzilli/Util/MockFuzzer.swift
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@ struct MockExecution: Execution {
}

class MockScriptRunner: ScriptRunner {
var processArguments: [String] = []

func run(_ script: String, withTimeout timeout: UInt32) -> Execution {
return MockExecution(outcome: .succeeded,
stdout: "",
Expand Down
4 changes: 3 additions & 1 deletion Sources/FuzzilliCli/Profiles/DuktapeProfile.swift
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,9 @@
import Fuzzilli

let duktapeProfile = Profile(
processArguments: ["--reprl"],
getProcessArguments: { (randomizingArguments: Bool) -> [String] in
return ["--reprl"]
},

processEnv: ["UBSAN_OPTIONS": "handle_segv=0"],

Expand Down
43 changes: 31 additions & 12 deletions Sources/FuzzilliCli/Profiles/JSCProfile.swift
Original file line number Diff line number Diff line change
Expand Up @@ -31,18 +31,37 @@ fileprivate let ForceFTLCompilationGenerator = CodeGenerator("ForceFTLCompilatio
}

let jscProfile = Profile(
processArguments: ["--validateOptions=true",
// No need to call functions thousands of times before they are JIT compiled
"--thresholdForJITSoon=10",
"--thresholdForJITAfterWarmUp=10",
"--thresholdForOptimizeAfterWarmUp=100",
"--thresholdForOptimizeAfterLongWarmUp=100",
"--thresholdForOptimizeSoon=100",
"--thresholdForFTLOptimizeAfterWarmUp=1000",
"--thresholdForFTLOptimizeSoon=1000",
// Enable bounds check elimination validation
"--validateBCE=true",
"--reprl"],
getProcessArguments: { (randomizingArguments: Bool) -> [String] in
var args = [
"--validateOptions=true",
// No need to call functions thousands of times before they are JIT compiled
"--thresholdForJITSoon=10",
"--thresholdForJITAfterWarmUp=10",
"--thresholdForOptimizeAfterWarmUp=100",
"--thresholdForOptimizeAfterLongWarmUp=100",
"--thresholdForOptimizeSoon=100",
"--thresholdForFTLOptimizeAfterWarmUp=1000",
"--thresholdForFTLOptimizeSoon=1000",
// Enable bounds check elimination validation
"--validateBCE=true",
"--reprl"]

guard randomizingArguments else { return args }

args.append("--useBaselineJIT=\(probability(0.9) ? "true" : "false")")
args.append("--useDFGJIT=\(probability(0.9) ? "true" : "false")")
args.append("--useFTLJIT=\(probability(0.9) ? "true" : "false")")
args.append("--useRegExpJIT=\(probability(0.9) ? "true" : "false")")
args.append("--useTailCalls=\(probability(0.9) ? "true" : "false")")
args.append("--optimizeRecursiveTailCalls=\(probability(0.9) ? "true" : "false")")
args.append("--useObjectAllocationSinking=\(probability(0.9) ? "true" : "false")")
args.append("--useArityFixupInlining=\(probability(0.9) ? "true" : "false")")
args.append("--useValueRepElimination=\(probability(0.9) ? "true" : "false")")
args.append("--useArchitectureSpecificOptimizations=\(probability(0.9) ? "true" : "false")")
args.append("--useAccessInlining=\(probability(0.9) ? "true" : "false")")

return args
},

processEnv: ["UBSAN_OPTIONS":"handle_segv=0"],

Expand Down
4 changes: 3 additions & 1 deletion Sources/FuzzilliCli/Profiles/JerryscriptProfile.swift
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,9 @@
import Fuzzilli

let jerryscriptProfile = Profile(
processArguments: ["--reprl-fuzzilli"],
getProcessArguments: { (randomizingArguments: Bool) -> [String] in
return ["--reprl-fuzzilli"]
},

// processEnv: [:],
processEnv: ["UBSAN_OPTIONS":"handle_segv=0"],
Expand Down
2 changes: 1 addition & 1 deletion Sources/FuzzilliCli/Profiles/Profile.swift
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
import Fuzzilli

struct Profile {
let processArguments: [String]
let getProcessArguments: (_: Bool) -> [String]
let processEnv: [String : String]
let codePrefix: String
let codeSuffix: String
Expand Down
4 changes: 3 additions & 1 deletion Sources/FuzzilliCli/Profiles/QjsProfile.swift
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,9 @@
import Fuzzilli

let qjsProfile = Profile(
processArguments: ["--reprl"],
getProcessArguments: { (randomizingArguments: Bool) -> [String] in
return ["--reprl"]
},

processEnv: ["UBSAN_OPTIONS": "handle_segv=0"],

Expand Down
5 changes: 4 additions & 1 deletion Sources/FuzzilliCli/Profiles/QtjsProfile.swift
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,10 @@ fileprivate let ForceQV4JITGenerator = CodeGenerator("ForceQV4JITGenerator", inp
}

let qtjsProfile = Profile(
processArguments: ["-reprl"],
getProcessArguments: { (randomizingArguments: Bool) -> [String] in
return ["-reprl"]
},

processEnv: ["UBSAN_OPTIONS":"handle_segv=0"],

codePrefix: """
Expand Down
48 changes: 40 additions & 8 deletions Sources/FuzzilliCli/Profiles/SpidermonkeyProfile.swift
Original file line number Diff line number Diff line change
Expand Up @@ -26,14 +26,46 @@ fileprivate let ForceSpidermonkeyIonGenerator = CodeGenerator("ForceSpidermonkey
}

let spidermonkeyProfile = Profile(
processArguments: [
"--baseline-warmup-threshold=10",
"--ion-warmup-threshold=100",
"--ion-check-range-analysis",
"--ion-extra-checks",
"--fuzzing-safe",
"--reprl",
],
getProcessArguments: { (randomizingArguments: Bool) -> [String] in
var args = [
"--baseline-warmup-threshold=10",
"--ion-warmup-threshold=100",
"--ion-check-range-analysis",
"--ion-extra-checks",
"--fuzzing-safe",
"--reprl"]

guard randomizingArguments else { return args }

args.append("--small-function-length=\(1<<Int.random(in: 7...12))")
args.append("--inlining-entry-threshold=\(1<<Int.random(in: 2...10))")
args.append("--gc-zeal=\(probability(0.5) ? UInt32(0) : UInt32(Int.random(in: 1...24)))")
args.append("--ion-scalar-replacement=\(probability(0.9) ? "on": "off")")
args.append("--ion-pruning=\(probability(0.9) ? "on": "off")")
args.append("--ion-range-analysis=\(probability(0.9) ? "on": "off")")
args.append("--ion-inlining=\(probability(0.9) ? "on": "off")")
args.append("--ion-gvn=\(probability(0.9) ? "on": "off")")
args.append("--ion-osr=\(probability(0.9) ? "on": "off")")
args.append("--ion-edgecase-analysis=\(probability(0.9) ? "on": "off")")
args.append("--nursery-size=\(1<<Int.random(in: 0...5))")
args.append("--nursery-strings=\(probability(0.9) ? "on": "off")")
args.append("--nursery-bigints=\(probability(0.9) ? "on": "off")")
args.append("--spectre-mitigations=\(probability(0.1) ? "on": "off")")
if probability(0.1) {
args.append("--no-native-regexp")
}
args.append("--ion-optimize-shapeguards=\(probability(0.9) ? "on": "off")")
args.append("--ion-licm=\(probability(0.9) ? "on": "off")")
args.append("--ion-instruction-reordering=\(probability(0.9) ? "on": "off")")
args.append("--cache-ir-stubs=\(probability(0.9) ? "on": "off")")
args.append(chooseUniform(from: ["--no-sse3", "--no-ssse3", "--no-sse41", "--no-sse42", "--enable-avx"]))
if probability(0.1) {
args.append("--ion-regalloc=testbed")
}
args.append(probability(0.9) ? "--enable-watchtower" : "--disable-watchtower")
args.append("--ion-sink=\(probability(0.0) ? "on": "off")") // disabled
return args
},

processEnv: ["UBSAN_OPTIONS": "handle_segv=0"],

Expand Down
47 changes: 39 additions & 8 deletions Sources/FuzzilliCli/Profiles/V8Profile.swift
Original file line number Diff line number Diff line change
Expand Up @@ -231,14 +231,45 @@ fileprivate let VerifyTypeTemplate = ProgramTemplate("VerifyTypeTemplate") { b i
}

let v8Profile = Profile(
processArguments: ["--expose-gc",
"--future",
"--harmony",
"--assert-types",
"--harmony-rab-gsab",
"--allow-natives-syntax",
"--interrupt-budget=1024",
"--fuzzing"],
getProcessArguments: { (randomizingArguments: Bool) -> [String] in
var args = [
"--expose-gc",
"--future",
"--harmony",
"--assert-types",
"--harmony-rab-gsab",
"--allow-natives-syntax",
"--interrupt-budget=1024",
"--fuzzing"]

guard randomizingArguments else { return args }

args.append(probability(0.9) ? "--sparkplug" : "--no-sparkplug")
args.append(probability(0.9) ? "--opt" : "--no-opt")
args.append(probability(0.9) ? "--lazy" : "--no-lazy")
args.append(probability(0.1) ? "--always-opt" : "--no-always-opt")
args.append(probability(0.1) ? "--always-osr" : "--no-always-osr")
args.append(probability(0.1) ? "--force-slow-path" : "--no-force-slow-path")
args.append(probability(0.9) ? "--turbo-move-optimization" : "--no-turbo-move-optimization")
args.append(probability(0.9) ? "--turbo-jt" : "--no-turbo-jt")
args.append(probability(0.9) ? "--turbo-loop-peeling" : "--no-turbo-loop-peeling")
args.append(probability(0.9) ? "--turbo-loop-variable" : "--no-turbo-loop-variable")
args.append(probability(0.9) ? "--turbo-loop-rotation" : "--no-turbo-loop-rotation")
args.append(probability(0.9) ? "--turbo-cf-optimization" : "--no-turbo-cf-optimization")
args.append(probability(0.9) ? "--turbo-escape" : "--no-turbo-escape")
args.append(probability(0.9) ? "--turbo-allocation-folding" : "--no-turbo-allocation-folding")
args.append(probability(0.9) ? "--turbo-instruction-scheduling" : "--no-turbo-instruction-scheduling")
args.append(probability(0.9) ? "--turbo-stress-instruction-scheduling" : "--no-turbo-stress-instruction-scheduling")
args.append(probability(0.9) ? "--turbo-store-elimination" : "--no-turbo-store-elimination")
args.append(probability(0.9) ? "--turbo-rewrite-far-jumps" : "--no-turbo-rewrite-far-jumps")
args.append(probability(0.9) ? "--turbo-optimize-apply" : "--no-turbo-optimize-apply")
args.append(chooseUniform(from: ["--no-enable-sse3", "--no-enable-ssse3", "--no-enable-sse4-1", "--no-enable-sse4-2", "--no-enable-avx", "--no-enable-avx2",]))
args.append(probability(0.9) ? "--turbo-load-elimination" : "--no-turbo-load-elimination")
args.append(probability(0.9) ? "--turbo-inlining" : "--no-turbo-inlining")
args.append(probability(0.9) ? "--turbo-splitting" : "--no-turbo-splitting")

return args
},

processEnv: [:],

Expand Down
4 changes: 3 additions & 1 deletion Sources/FuzzilliCli/Profiles/XSProfile.swift
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,9 @@
import Fuzzilli

let xsProfile = Profile(
processArguments: ["-f"],
getProcessArguments: { (randomizingArguments: Bool) -> [String] in
return ["-f"]
},

processEnv: ["UBSAN_OPTIONS":"handle_segv=0"],

Expand Down
4 changes: 3 additions & 1 deletion Sources/FuzzilliCli/main.swift
Original file line number Diff line number Diff line change
Expand Up @@ -107,6 +107,7 @@ Options:
types: Programs written to disk also contain variable type information as
determined by Fuzzilli as comments
all: All of the above
--argumentRandomization : Enable JS engine argument randomization
""")
exit(0)
}
Expand Down Expand Up @@ -163,6 +164,7 @@ let collectRuntimeTypes = args.has("--collectRuntimeTypes")
let diagnostics = args.has("--diagnostics")
let inspect = args["--inspect"]
let swarmTesting = args.has("--swarmTesting")
let randomizingArguments = args.has("--argumentRandomization")

guard numJobs >= 1 else {
configError("Must have at least 1 job")
Expand Down Expand Up @@ -365,7 +367,7 @@ for (generator, var weight) in (additionalCodeGenerators + regularCodeGenerators

func makeFuzzer(for profile: Profile, with configuration: Configuration) -> Fuzzer {
// A script runner to execute JavaScript code in an instrumented JS engine.
let runner = REPRL(executable: jsShellPath, processArguments: profile.processArguments, processEnvironment: profile.processEnv)
let runner = REPRL(executable: jsShellPath, processArguments: profile.getProcessArguments(randomizingArguments), processEnvironment: profile.processEnv)

let engine: FuzzEngine
switch engineName {
Expand Down