From 00e751f18e761e2bc5ddb32aee4bd3dd25c57823 Mon Sep 17 00:00:00 2001 From: Sergey Sorokin Date: Fri, 23 Feb 2018 19:55:02 -0500 Subject: [PATCH] target-arm: Stage 2 permission fault was fixed in AArch32 state As described in AArch32.CheckS2Permission an instruction fetch fails if XN bit is set or there is no read permission for the address. Backports commit dfda68377e20943f474505e75238cb96bc6874bf from qemu --- msvc/unicorn/qapi-visit.c | 68 +++++++++++++++++++++++++++++++++++++++ qemu/target-arm/helper.c | 4 ++- 2 files changed, 71 insertions(+), 1 deletion(-) diff --git a/msvc/unicorn/qapi-visit.c b/msvc/unicorn/qapi-visit.c index bde9499e..fa09fdab 100644 --- a/msvc/unicorn/qapi-visit.c +++ b/msvc/unicorn/qapi-visit.c @@ -48,6 +48,10 @@ void visit_type_DummyForceArrays(Visitor *v, const char *name, DummyForceArrays visit_check_struct(v, &err); out_obj: visit_end_struct(v); + if (err && visit_is_input(v)) { + qapi_free_DummyForceArrays(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -111,6 +115,10 @@ void visit_type_X86CPUFeatureWordInfo(Visitor *v, const char *name, X86CPUFeatur visit_check_struct(v, &err); out_obj: visit_end_struct(v); + if (err && visit_is_input(v)) { + qapi_free_X86CPUFeatureWordInfo(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -137,6 +145,10 @@ void visit_type_X86CPUFeatureWordInfoList(Visitor *v, const char *name, X86CPUFe error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_X86CPUFeatureWordInfoList(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -170,6 +182,10 @@ void visit_type_anyList(Visitor *v, const char *name, anyList **obj, Error **err error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_anyList(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -196,6 +212,10 @@ void visit_type_boolList(Visitor *v, const char *name, boolList **obj, Error **e error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_boolList(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -222,6 +242,10 @@ void visit_type_int16List(Visitor *v, const char *name, int16List **obj, Error * error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_int16List(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -248,6 +272,10 @@ void visit_type_int32List(Visitor *v, const char *name, int32List **obj, Error * error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_int32List(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -274,6 +302,10 @@ void visit_type_int64List(Visitor *v, const char *name, int64List **obj, Error * error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_int64List(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -300,6 +332,10 @@ void visit_type_int8List(Visitor *v, const char *name, int8List **obj, Error **e error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_int8List(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -326,6 +362,10 @@ void visit_type_intList(Visitor *v, const char *name, intList **obj, Error **err error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_intList(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -352,6 +392,10 @@ void visit_type_numberList(Visitor *v, const char *name, numberList **obj, Error error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_numberList(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -378,6 +422,10 @@ void visit_type_sizeList(Visitor *v, const char *name, sizeList **obj, Error **e error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_sizeList(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -404,6 +452,10 @@ void visit_type_strList(Visitor *v, const char *name, strList **obj, Error **err error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_strList(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -430,6 +482,10 @@ void visit_type_uint16List(Visitor *v, const char *name, uint16List **obj, Error error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_uint16List(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -456,6 +512,10 @@ void visit_type_uint32List(Visitor *v, const char *name, uint32List **obj, Error error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_uint32List(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -482,6 +542,10 @@ void visit_type_uint64List(Visitor *v, const char *name, uint64List **obj, Error error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_uint64List(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } @@ -508,6 +572,10 @@ void visit_type_uint8List(Visitor *v, const char *name, uint8List **obj, Error * error_propagate(errp, err); err = NULL; visit_end_list(v); + if (err && visit_is_input(v)) { + qapi_free_uint8List(*obj); + *obj = NULL; + } out: error_propagate(errp, err); } diff --git a/qemu/target-arm/helper.c b/qemu/target-arm/helper.c index 003149e1..dc935376 100644 --- a/qemu/target-arm/helper.c +++ b/qemu/target-arm/helper.c @@ -5963,7 +5963,9 @@ static int get_S2prot(CPUARMState *env, int s2ap, int xn) prot |= PAGE_WRITE; } if (!xn) { - prot |= PAGE_EXEC; + if (arm_el_is_aa64(env, 2) || prot & PAGE_READ) { + prot |= PAGE_EXEC; + } } return prot; }