ref: 74c1f4730b548c3499e59ac0c2f2aadfcd7727c5
parent: 7a503757b1251c2746df7bdcd891814c1518cc28
author: Jacob Moody <moody@posixcafe.org>
date: Sat Jan 6 22:04:35 EST 2024
6?, 8?, libc: add JMPF instruction In 6? and 8? JMP works a bit uniquely, when passed a function name it always encodes as a JMP* instead of a JMP. This means JMP myfunc(SB) always assume that myfunc is a function pointer, not a function itself. The new JMPF instead has the same semantics as CALL and matches B and JMP in other assemblers. This allows for a small optimization in our 386 and amd64 entrypoint by avoiding a jump between _main and _callmain.
--- a/sys/src/cmd/6a/lex.c
+++ b/sys/src/cmd/6a/lex.c
@@ -433,6 +433,7 @@
"JCXZ", LTYPER, AJCXZ,
"JMP", LTYPEC, AJMP,
+ "JMPF", LTYPEC, AJMPF,
"LAHF", LTYPE0, ALAHF,
"LARL", LTYPE3, ALARL,
"LARW", LTYPE3, ALARW,
--- a/sys/src/cmd/6c/6.out.h
+++ b/sys/src/cmd/6c/6.out.h
@@ -713,6 +713,8 @@
ADPPD,
ADPPS,
+ AJMPF,
+
ALAST
};
--- a/sys/src/cmd/6l/l.h
+++ b/sys/src/cmd/6l/l.h
@@ -170,6 +170,7 @@
Zilo_m,
Ziqo_m,
Zjmp,
+ Zjmpf,
Zloop,
Zo_iw,
Zm_o,
--- a/sys/src/cmd/6l/optab.c
+++ b/sys/src/cmd/6l/optab.c
@@ -295,6 +295,11 @@
Ynone, Ybr, Zjmp, 1,
0
};
+uchar yjmpf[] =
+{
+ Ynone, Ybr, Zjmpf, 1,
+ 0
+};
uchar yfmvd[] =
{
@@ -717,6 +722,7 @@
{ AJLT, yjcond, Px, 0x7c,0x8c },
{ AJMI, yjcond, Px, 0x78,0x88 },
{ AJMP, yjmp, Px, 0xff,(04),0xeb,0xe9 },
+ { AJMPF, yjmpf, Px, 0xe9 },
{ AJNE, yjcond, Px, 0x75,0x85 },
{ AJOC, yjcond, Px, 0x71,0x81,(00) },
{ AJOS, yjcond, Px, 0x70,0x80,(00) },
--- a/sys/src/cmd/6l/pass.c
+++ b/sys/src/cmd/6l/pass.c
@@ -142,7 +142,7 @@
return;
if(p->as == ATEXT)
curtext = p;
- if(p->as == AJMP)
+ if(p->as == AJMP || p->as == AJMPF)
if((q = p->pcond) != P) {
p->mark = 1;
p = q;
@@ -319,7 +319,7 @@
for(p = firstp; p != P; p = p->link) {
if(p->as == ATEXT)
curtext = p;
- if(p->as == ACALL || p->as == ARET) {
+ if(p->as == ACALL || p->as == ARET || p->as == AJMPF) {
s = p->to.sym;
if(s) {
if(debug['c'])
--- a/sys/src/cmd/6l/span.c
+++ b/sys/src/cmd/6l/span.c
@@ -1360,6 +1360,7 @@
}
break;
+ case Zjmpf:
case Zcall:
q = p->pcond;
if(q) {
--- a/sys/src/cmd/8a/lex.c
+++ b/sys/src/cmd/8a/lex.c
@@ -372,6 +372,7 @@
"JCXZ", LTYPER, AJCXZ,
"JMP", LTYPEC, AJMP,
+ "JMPF", LTYPEC, AJMPF,
"LAHF", LTYPE0, ALAHF,
"LARL", LTYPE3, ALARL,
"LARW", LTYPE3, ALARW,
--- a/sys/src/cmd/8c/8.out.h
+++ b/sys/src/cmd/8c/8.out.h
@@ -585,6 +585,8 @@
API2FW,
API2FL,
+ AJMPF,
+
/* add new operations here. nowhere else. here. */
ALAST
};
--- a/sys/src/cmd/8l/l.h
+++ b/sys/src/cmd/8l/l.h
@@ -158,6 +158,7 @@
Zil_rp,
Zilo_m,
Zjmp,
+ Zjmpf,
Zloop,
Zm_o,
Zm_r,
--- a/sys/src/cmd/8l/optab.c
+++ b/sys/src/cmd/8l/optab.c
@@ -240,6 +240,11 @@
Ynone, Ybr, Zjmp, 1,
0
};
+uchar yjmpf[] =
+{
+ Ynone, Ybr, Zjmp, 1,
+ 0
+};
uchar yfmvd[] =
{
@@ -563,6 +568,7 @@
{ AJLT, yjcond, Px, 0x7c,0x8c },
{ AJMI, yjcond, Px, 0x78,0x88 },
{ AJMP, yjmp, Px, 0xff,(04),0xeb,0xe9 },
+ { AJMPF, yjmpf, Px, 0xe9 },
{ AJNE, yjcond, Px, 0x75,0x85 },
{ AJOC, yjcond, Px, 0x71,0x81,(00) },
{ AJOS, yjcond, Px, 0x70,0x80,(00) },
--- a/sys/src/cmd/8l/pass.c
+++ b/sys/src/cmd/8l/pass.c
@@ -136,7 +136,7 @@
return;
if(p->as == ATEXT)
curtext = p;
- if(p->as == AJMP)
+ if(p->as == AJMP || p->as == AJMPF)
if((q = p->pcond) != P) {
p->mark = 1;
p = q;
@@ -303,7 +303,7 @@
for(p = firstp; p != P; p = p->link) {
if(p->as == ATEXT)
curtext = p;
- if(p->as == ACALL || p->as == ARET) {
+ if(p->as == ACALL || p->as == ARET || p->as == AJMPF) {
s = p->to.sym;
if(s) {
if(debug['c'])
--- a/sys/src/cmd/8l/span.c
+++ b/sys/src/cmd/8l/span.c
@@ -1151,6 +1151,7 @@
}
break;
+ case Zjmpf:
case Zcall:
q = p->pcond;
if(q) {
--- a/sys/src/libc/386/main9.s
+++ b/sys/src/libc/386/main9.s
@@ -3,5 +3,4 @@
MOVL $main(SB), AX
PUSHL AX
PUSHL $0
- MOVL $_callmain(SB), AX
- JMP* AX
+ JMPF _callmain(SB)
--- a/sys/src/libc/386/main9p.s
+++ b/sys/src/libc/386/main9p.s
@@ -3,8 +3,7 @@
MOVL $_profmain(SB), AX
PUSHL AX
PUSHL $0
- MOVL $_callmain(SB), AX
- JMP* AX
+ JMPF _callmain(SB)
MOVL $_profin(SB), AX /* force loading of profile */
TEXT _saveret(SB), 1, $0
--- a/sys/src/libc/amd64/main9.s
+++ b/sys/src/libc/amd64/main9.s
@@ -3,5 +3,4 @@
MOVQ $main(SB), RARG
PUSHQ RARG
PUSHQ $0
- MOVQ $_callmain(SB), AX
- JMP* AX
+ JMPF _callmain(SB)
--- a/sys/src/libc/amd64/main9p.s
+++ b/sys/src/libc/amd64/main9p.s
@@ -3,8 +3,7 @@
MOVQ $_profmain(SB), RARG
PUSHQ RARG
PUSHQ $0
- MOVQ $_callmain(SB), AX
- JMP* AX
+ JMPF _callmain(SB)
MOVQ $_profin(SB), AX /* force loading of profile */