1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105
|
From: Ben Harris <bjh21@bjh21.me.uk>
Date: Thu, 9 Jan 2025 21:54:14 +0000
X-Dgit-Generated: 4.21c-5~1.gbp3dcdb9 f3ad11aa08a06c8862b7c49b45ced0c78350d1e0
Subject: Replace all PyObject_GetAttrString() with ...Optional...()
This suppresses the AttributeError that would otherwise be raised when
the attribute doesn't exist. It doesn't suppress other exceptions,
though, and we still don't handle those properly.
This enables compiling with Python 3.13. Without this patch, the last
AttributeError from PyObject_GetAttrString() seems to get saved and
raised when we next call into Python code, which happens in init_py().
Unfortunately, using PyObject_GetOptionalAttrString() means that this
patch doesn't work with any Python older than 3.13.
Bug-Debian: 1091402
---
diff --git a/src/afl-fuzz-python.c b/src/afl-fuzz-python.c
index 873b25e..2a91c98 100644
--- a/src/afl-fuzz-python.c
+++ b/src/afl-fuzz-python.c
@@ -220,45 +220,50 @@ static py_mutator_t *init_py_module(afl_state_t *afl, u8 *module_name) {
if (py_module != NULL) {
u8 py_notrim = 0;
- py_functions[PY_FUNC_INIT] = PyObject_GetAttrString(py_module, "init");
+ PyObject_GetOptionalAttrString(py_module, "init",
+ &py_functions[PY_FUNC_INIT]);
if (!py_functions[PY_FUNC_INIT]) {
WARNF("init function not found in python module");
}
- py_functions[PY_FUNC_FUZZ] = PyObject_GetAttrString(py_module, "fuzz");
+ PyObject_GetOptionalAttrString(py_module, "fuzz",
+ &py_functions[PY_FUNC_FUZZ]);
if (!py_functions[PY_FUNC_FUZZ])
- py_functions[PY_FUNC_FUZZ] = PyObject_GetAttrString(py_module, "mutate");
- py_functions[PY_FUNC_DESCRIBE] =
- PyObject_GetAttrString(py_module, "describe");
- py_functions[PY_FUNC_FUZZ_COUNT] =
- PyObject_GetAttrString(py_module, "fuzz_count");
- py_functions[PY_FUNC_POST_PROCESS] =
- PyObject_GetAttrString(py_module, "post_process");
- py_functions[PY_FUNC_INIT_TRIM] =
- PyObject_GetAttrString(py_module, "init_trim");
- py_functions[PY_FUNC_POST_TRIM] =
- PyObject_GetAttrString(py_module, "post_trim");
- py_functions[PY_FUNC_TRIM] = PyObject_GetAttrString(py_module, "trim");
- py_functions[PY_FUNC_HAVOC_MUTATION] =
- PyObject_GetAttrString(py_module, "havoc_mutation");
- py_functions[PY_FUNC_HAVOC_MUTATION_PROBABILITY] =
- PyObject_GetAttrString(py_module, "havoc_mutation_probability");
- py_functions[PY_FUNC_QUEUE_GET] =
- PyObject_GetAttrString(py_module, "queue_get");
- py_functions[PY_FUNC_FUZZ_SEND] =
- PyObject_GetAttrString(py_module, "fuzz_send");
- py_functions[PY_FUNC_POST_RUN] =
- PyObject_GetAttrString(py_module, "post_run");
- py_functions[PY_FUNC_SPLICE_OPTOUT] =
- PyObject_GetAttrString(py_module, "splice_optout");
+ PyObject_GetOptionalAttrString(py_module, "mutate",
+ &py_functions[PY_FUNC_FUZZ]);
+ PyObject_GetOptionalAttrString(py_module, "describe",
+ &py_functions[PY_FUNC_DESCRIBE]);
+ PyObject_GetOptionalAttrString(py_module, "fuzz_count",
+ &py_functions[PY_FUNC_FUZZ_COUNT]);
+ PyObject_GetOptionalAttrString(py_module, "post_process",
+ &py_functions[PY_FUNC_POST_PROCESS]);
+ PyObject_GetOptionalAttrString(py_module, "init_trim",
+ &py_functions[PY_FUNC_INIT_TRIM]);
+ PyObject_GetOptionalAttrString(py_module, "post_trim",
+ &py_functions[PY_FUNC_POST_TRIM]);
+ PyObject_GetOptionalAttrString(py_module, "trim",
+ &py_functions[PY_FUNC_TRIM]);
+ PyObject_GetOptionalAttrString(py_module, "havoc_mutation",
+ &py_functions[PY_FUNC_HAVOC_MUTATION]);
+ PyObject_GetOptionalAttrString(py_module, "havoc_mutation_probability",
+ &py_functions[PY_FUNC_HAVOC_MUTATION_PROBABILITY]);
+ PyObject_GetOptionalAttrString(py_module, "queue_get",
+ &py_functions[PY_FUNC_QUEUE_GET]);
+ PyObject_GetOptionalAttrString(py_module, "fuzz_send",
+ &py_functions[PY_FUNC_FUZZ_SEND]);
+ PyObject_GetOptionalAttrString(py_module, "post_run",
+ &py_functions[PY_FUNC_POST_RUN]);
+ PyObject_GetOptionalAttrString(py_module, "splice_optout",
+ &py_functions[PY_FUNC_SPLICE_OPTOUT]);
if (py_functions[PY_FUNC_SPLICE_OPTOUT]) { afl->custom_splice_optout = 1; }
- py_functions[PY_FUNC_QUEUE_NEW_ENTRY] =
- PyObject_GetAttrString(py_module, "queue_new_entry");
- py_functions[PY_FUNC_INTROSPECTION] =
- PyObject_GetAttrString(py_module, "introspection");
- py_functions[PY_FUNC_DEINIT] = PyObject_GetAttrString(py_module, "deinit");
+ PyObject_GetOptionalAttrString(py_module, "queue_new_entry",
+ &py_functions[PY_FUNC_QUEUE_NEW_ENTRY]);
+ PyObject_GetOptionalAttrString(py_module, "introspection",
+ &py_functions[PY_FUNC_INTROSPECTION]);
+ PyObject_GetOptionalAttrString(py_module, "deinit",
+ &py_functions[PY_FUNC_DEINIT] );
if (!py_functions[PY_FUNC_DEINIT])
WARNF("deinit function not found in python module");
|