summaryrefslogtreecommitdiffstats
path: root/Python
diff options
context:
space:
mode:
authorpenguin_wwy <940375606@qq.com>2022-01-06 11:38:35 (GMT)
committerGitHub <noreply@github.com>2022-01-06 11:38:35 (GMT)
commit3db762db72cc0da938614b1e414abb1e12ca4094 (patch)
treeeef08b55d931522d2f83ed7b6f2383d27d8a4ffe /Python
parent35d6540c904ef07b8602ff014e520603f84b5886 (diff)
downloadcpython-3db762db72cc0da938614b1e414abb1e12ca4094.zip
cpython-3db762db72cc0da938614b1e414abb1e12ca4094.tar.gz
cpython-3db762db72cc0da938614b1e414abb1e12ca4094.tar.bz2
bpo-46031: add POP_JUMP_IF_NOT_NONE and POP_JUMP_IF_NONE (GH-30019)
Diffstat (limited to 'Python')
-rw-r--r--Python/ceval.c24
-rw-r--r--Python/compile.c27
-rw-r--r--Python/opcode_targets.h12
3 files changed, 57 insertions, 6 deletions
diff --git a/Python/ceval.c b/Python/ceval.c
index b4ac9ec..86d834c 100644
--- a/Python/ceval.c
+++ b/Python/ceval.c
@@ -4049,6 +4049,30 @@ check_eval_breaker:
DISPATCH();
}
+ TARGET(POP_JUMP_IF_NOT_NONE) {
+ PyObject *value = POP();
+ if (!Py_IsNone(value)) {
+ Py_DECREF(value);
+ JUMPTO(oparg);
+ CHECK_EVAL_BREAKER();
+ DISPATCH();
+ }
+ Py_DECREF(value);
+ DISPATCH();
+ }
+
+ TARGET(POP_JUMP_IF_NONE) {
+ PyObject *value = POP();
+ if (Py_IsNone(value)) {
+ Py_DECREF(value);
+ JUMPTO(oparg);
+ CHECK_EVAL_BREAKER();
+ DISPATCH();
+ }
+ Py_DECREF(value);
+ DISPATCH();
+ }
+
TARGET(JUMP_IF_FALSE_OR_POP) {
PyObject *cond = TOP();
int err;
diff --git a/Python/compile.c b/Python/compile.c
index 3a39075..625a07b 100644
--- a/Python/compile.c
+++ b/Python/compile.c
@@ -1110,6 +1110,8 @@ stack_effect(int opcode, int oparg, int jump)
case POP_JUMP_IF_FALSE:
case POP_JUMP_IF_TRUE:
+ case POP_JUMP_IF_NONE:
+ case POP_JUMP_IF_NOT_NONE:
return -1;
case LOAD_GLOBAL:
@@ -8519,6 +8521,21 @@ optimize_basic_block(struct compiler *c, basicblock *bb, PyObject *consts)
bb->b_instr[i+1].i_opcode = NOP;
}
break;
+ case IS_OP:
+ cnt = get_const_value(inst->i_opcode, oparg, consts);
+ if (cnt == NULL) {
+ goto error;
+ }
+ int jump_op = i+2 < bb->b_iused ? bb->b_instr[i+2].i_opcode : 0;
+ if (Py_IsNone(cnt) && (jump_op == POP_JUMP_IF_FALSE || jump_op == POP_JUMP_IF_TRUE)) {
+ unsigned char nextarg = bb->b_instr[i+1].i_oparg;
+ inst->i_opcode = NOP;
+ bb->b_instr[i+1].i_opcode = NOP;
+ bb->b_instr[i+2].i_opcode = nextarg ^ (jump_op == POP_JUMP_IF_FALSE) ?
+ POP_JUMP_IF_NOT_NONE : POP_JUMP_IF_NONE;
+ }
+ Py_DECREF(cnt);
+ break;
}
break;
}
@@ -8611,6 +8628,14 @@ optimize_basic_block(struct compiler *c, basicblock *bb, PyObject *consts)
break;
}
break;
+ case POP_JUMP_IF_NOT_NONE:
+ case POP_JUMP_IF_NONE:
+ switch (target->i_opcode) {
+ case JUMP_ABSOLUTE:
+ case JUMP_FORWARD:
+ i -= jump_thread(inst, target, inst->i_opcode);
+ }
+ break;
case POP_JUMP_IF_FALSE:
switch (target->i_opcode) {
case JUMP_ABSOLUTE:
@@ -8766,6 +8791,8 @@ normalize_basic_block(basicblock *bb) {
case JUMP_FORWARD:
bb->b_nofallthrough = 1;
/* fall through */
+ case POP_JUMP_IF_NOT_NONE:
+ case POP_JUMP_IF_NONE:
case POP_JUMP_IF_FALSE:
case POP_JUMP_IF_TRUE:
case JUMP_IF_FALSE_OR_POP:
diff --git a/Python/opcode_targets.h b/Python/opcode_targets.h
index e9f1a48..7ba4566 100644
--- a/Python/opcode_targets.h
+++ b/Python/opcode_targets.h
@@ -127,20 +127,20 @@ static void *opcode_targets[256] = {
&&TARGET_STORE_FAST,
&&TARGET_DELETE_FAST,
&&TARGET_JUMP_IF_NOT_EG_MATCH,
- &&TARGET_STORE_FAST__LOAD_FAST,
- &&TARGET_LOAD_FAST__LOAD_CONST,
+ &&TARGET_POP_JUMP_IF_NOT_NONE,
+ &&TARGET_POP_JUMP_IF_NONE,
&&TARGET_RAISE_VARARGS,
- &&TARGET_LOAD_CONST__LOAD_FAST,
+ &&TARGET_STORE_FAST__LOAD_FAST,
&&TARGET_MAKE_FUNCTION,
&&TARGET_BUILD_SLICE,
- &&TARGET_STORE_FAST__STORE_FAST,
+ &&TARGET_LOAD_FAST__LOAD_CONST,
&&TARGET_MAKE_CELL,
&&TARGET_LOAD_CLOSURE,
&&TARGET_LOAD_DEREF,
&&TARGET_STORE_DEREF,
&&TARGET_DELETE_DEREF,
- &&_unknown_opcode,
- &&_unknown_opcode,
+ &&TARGET_LOAD_CONST__LOAD_FAST,
+ &&TARGET_STORE_FAST__STORE_FAST,
&&TARGET_CALL_FUNCTION_EX,
&&_unknown_opcode,
&&TARGET_EXTENDED_ARG,