#403 M68K: Hack to stop SetPatch loading could be cleaner

m68k-amiga
open-fixed
Shell/DOS (109)
5
2013-02-21
2012-04-04
Mark K
No

Currently AROS M68K patches LoadSeg() to ensure that SetPatch does not run, which is a bit of an ugly hack.

SetPatch checks whether it is already installed by searching for a semaphore named "« SetPatch »". Rather than patching LoadSeg(), it would be better to install a dummy semaphore so SetPatch thinks it has already been installed. As a benefit of that, you can have SetPatch print an arbitrary message (when run without QUIET argument).

To achieve that, a couple of fields near the "« SetPatch »" SignalSemaphore structure need to be set appropriately.

Offset Description
$2E.L Points to list of patches (see below).
$3A.W SetPatch major version. Must be non-zero.
$3C.W SetPatch minor version.

The longword at offset $2E should be set to point to a 0 longword. Then SetPatch will just print "None." for the list of installed patches.

Alternatively, you could use a dummy list giving some strings to show when SetPatch is run. E.g. something like "AROS SetPatch dummy patch". Or maybe an AROS version string?

About the patch list format. Each entry looks like this (SetPatch uses AddTail() to add entries to this list when it installs patches):

FirstPatch: dc.l SecondPatch
dc.l ???
dc.b "First patch description",0

SecondPatch: dc.l ThirdPatch
dc.l ???
dc.b "Second patch description",0

ThirdPatch: dc.l 0 ;Not a patch, indicates end of list

Discussion

  • Mark K

    Mark K - 2012-04-05

    The above info applies to SetPatch on Workbench 2.x and later disks.

    SetPatch on Workbench 1.3 uses a different method to detect whether it has already been installed. The WB 1.3 SetPatch does FindPort("SetPatch-01"). So creating a dummy message port with that name should be enough to fool it into not installing any patches.

     
  • Mark K

    Mark K - 2012-04-05

    It turns out that SetPatch version 37.x (on Workbench 2.04/2.05) uses yet another method to detect whether it has been installed. (SetPatch v38 on WB 2.1 uses the same method as SetPatch v39+.)

    SetPatch v37 calls FindPort("SetPatch Port"). It expects this data to be present at offsets from the MsgPort address:
    $22.W SetPatch major version
    $24.W SetPatch minor version
    $26.L Pointer to table of patches (see below)
    $2A.L Size of each entry in patch table; SetPatch uses $20
    $2E.W ??? Not sure; SetPatch puts 2 here

    If the longword at offset $26 points to a zero longword, SetPatch will think no patches have been installed and just exit. It's possible to use a fake patch list to get SetPatch to output text of your choice.

    The patch table consists of a number of fixed-size entries, like this. Entry size is as given in MsgPort+$2A.
    Offset Description
    0.L Non-zero if patch entry is valid. Zero denotes the end of the table.
    4.L Pointer to description string, or zero for no description.
    8 to size-1 Don't care (for our purposes)

    So for example you could put 8 at MsgPort+$2A, and have a dummy patch list like this:
    PatchTable
    dc.l 1
    dc.l FirstString
    dc.l 1
    dc.l 2ndString
    dc.l 1
    dc.l ThirdString
    dc.l 0 ;End of table

    FirstString:
    dc.b "First patch string",0
    SecondString:
    dc.b "Second line of text",0
    ThirdString:
    dc.b "Final line of text",0

    Or a clever/hacky way to save some memory... Have the length field at MsgPort+$2A be 4, and
    PatchTable
    dc.l 1
    dc.l FirstString
    dc.l SecondString
    dc.l ThirdString
    dc.l 0

     
  • Jason S. McMullan

    • assigned_to: nobody --> ezrec
     
  • Jason S. McMullan

    • status: open --> open-fixed
     
  • Jason S. McMullan

    Fixed in ABIv1 SVN r46663, r46664, r46665

     
  • Mark K

    Mark K - 2013-02-21

    Just for your information/interest... SetPatch 1.38 would probably run without problems under the AROS ROM. It checks library versions before installing patches, so on AROS should not install any. The only "bad" thing it does is write 0.w to address $F80000 and write 0.l to $000000. (It writes to $F80000 to ensure the Amiga 1000 Kickstart RAM is write-protected, since some methods of resetting can leave it write-enabled.)

    You do still need a dummy SetPatch-01 port though, to prevent the original SetPatch (3844 bytes long, datestamp 13-Aug-88) from patching Exec/Alert(), which it does unconditionally unless the dummy port is present.

     

Log in to post a comment.

Get latest updates about Open Source Projects, Conferences and News.

Sign up for the SourceForge newsletter:





No, thanks