Hello everybody,
in the master branch, marss/ptlsim/x86/decode-complex.cpp, lines 2048+,
case 0xfa: { // cli
EndOfDecode();
// this << TransOp(OP_collcc, REG_temp0, REG_zf, REG_cf, REG_of,
// 3, 0, 0, FLAGS_DEFAULT_ALU);
TransOp ast(OP_ast, REG_temp1, REG_temp0, REG_zero, REG_zero, 3);
ast.riptaken = L_ASSIST_CLI;
and lines 2061+,
case 0xfb: { // sti
EndOfDecode();
// this << TransOp(OP_collcc, REG_temp0, REG_zf, REG_cf, REG_of,
// 3, 0, 0, FLAGS_DEFAULT_ALU);
TransOp ast(OP_ast, REG_temp1, REG_temp0, REG_zero, REG_zero, 3);
ast.riptaken = L_ASSIST_STI;
The lightweight assist functions are called with uninitialized values of the ra
parameter. Lines 231+,
W64 l_assist_sti(Context& ctx, W64 ra, W64 rb, W64 rc, W16 raflags,
W16 rbflags, W16 rcflags, W16& flags) {
W16 current_flags = (W16)ra;
current_flags |= IF_MASK;
flags = current_flags;
and lines 254+,
W64 l_assist_cli(Context& ctx, W64 ra, W64 rb, W64 rc, W16 raflags,
W16 rbflags, W16 rcflags, W16& flags) {
W16 current_flags = (W16)ra;
current_flags &= ~IF_MASK;
flags = current_flags;
Now, the unintialized ra parameter might have FLAG_INV set. This will make the
assist uop fail and can cause indefinite re-issues of this and preceding
not-yet-committed uops if the uninitialized REG_temp0/1 registers remain
unchanged.
Changing the
W16 current_flags = (W16)ra;
lines to
W16 current_flags = (W16)ctx.reg_flags;
worked for me. (However, this might not be quite clean with regard to uop
issue vs commit semantics.)
I came across this error when investigating spurious Linux kernel freezes after
scheduler timer interrupts.
Regards,
gunnar.
_______________________________________________
http://www.marss86.org
Marss86-Devel mailing list
[email protected]
https://www.cs.binghamton.edu/mailman/listinfo/marss86-devel