ME cpu has two unknown instructions

Discuss the development of new homebrew software, tools and libraries.

Moderators: cheriff, TyRaNiD

Post Reply
hlide
Posts: 739
Joined: Sun Sep 10, 2006 2:31 am

ME cpu has two unknown instructions

Post by hlide »

when looking at mips-opc.c i was intrigued to see them :

Code: Select all

{ "ldl", "t,o(b)", 0x68000000, 0xfc000000, LDD|WR_t|RD_b, 0, I3|AL },
{ "sdl", "t,o(b)", 0xb0000000, 0xfc000000, SM|RD_t|RD_b, 0, I3|AL },
are "defined" for allegrex where as :

Code: Select all

{ "ldr", "t,o(b)", 0x6c000000, 0xfc000000, LDD|WR_t|RD_b, 0, I3 },
{ "sdr", "t,o(b)", 0xb4000000, 0xfc000000, SM|RD_t|RD_b, 0, I3 },
are not "defined" for allegrex.

PSP is not a MIPS64, so PSP shouldn't know those both instructions which are for unaligned doubleword load/store.

There is only one possibilty : ldl/sdl are special instructions which have a different goal.

Indeed they seem to be used a lot on ME processor, just one example :

Code: Select all

sub0(arg1, arg2, arg3):
        addiu      $sp, $sp, -0x10
        sw         $ra, 0xC($sp)
        sw         $s2, 0x8($sp)
        move       $s2, $a2
        sw         $s1, 0x4($sp)
        move       $s1, $a1
        sw         $s0, 0x0($sp)
        move       $s0, $a0
        move       $a0, $zr         # int timeout = 0;

0:      ldl        $a1, 0x200($a3)  # loop: ready = vme_bus[0x200]; (?)
        addiu      $a0, $a0, 0x1    # timeout++;
        andi       $v0, $a1, 0x1
        bnez       $v0, 1f          # if (ready & 1) goto goon; 
        slti       $v1, $a0, 0x1000
        bnez       $v1, 0b          # if &#40;timeout < 0x1000&#41; goto loop;  
        nop        
        jal        sub1             # sub1&#40;0xD&#41;; // reset ?
        li         $a0, 0xD

1&#58;      sdl        $s0, 0x200&#40;$a3&#41;  # goon&#58; vme_bus&#91;0x200&#93; = arg1; &#40;?&#41;
        sdl        $s1, 0x201&#40;$a3&#41;  #       vme_bus&#91;0x201&#93; = arg2; &#40;?&#41;
        sdl        $s2, 0x202&#40;$a3&#41;  #       vme_bus&#91;0x202&#93; = arg3; &#40;?&#41;
        move       $v0, $zr
        sdl        $v0, 0x203&#40;$a3&#41;  #       vme_bus&#91;0x203&#93; = 0; &#40;?&#41;
        lw         $ra, 0xC&#40;$sp&#41;
        lw         $s2, 0x8&#40;$sp&#41;
        lw         $s1, 0x4&#40;$sp&#41;
        lw         $s0, 0x0&#40;$sp&#41;
        jr         $ra
        addiu      $sp, $sp, 0x10
two remarks :

- $a3 is a dummy register so i suspect those instruction not to have a base register (their base opcodes seem to be more like 0x68E00000 and 0xB0E00000 than 0x68000000 and 0xB0000000)
- the offset should probably be an immediate (the biggest value I found out is 0x58F, which an immediate value encoded less than 12 bits).

so i suspect those both instructions to be something like :

ldl $v0, 0x200($a3) ==> mfvme $v0, $200 <=> $v0 = vme_bus[0x200]
sdl $v0, 0x200($a3) ==> mtvme $v0, $200 <=> vme_bus[0x200] = $v0

is it for VME ? is it for AVC decoder ? dunno.
adrahil
Posts: 274
Joined: Thu Mar 16, 2006 1:55 am

Post by adrahil »

Very interesting stuff :)
Post Reply