Patch to properly handle WORD sized symbol relocations by SainT.
authorShamus Hammons <jlhamm@acm.org>
Wed, 4 Oct 2017 14:31:20 +0000 (09:31 -0500)
committerShamus Hammons <jlhamm@acm.org>
Wed, 4 Oct 2017 14:31:20 +0000 (09:31 -0500)
Version now at 1.5.2.

rln.c
rln.h

diff --git a/rln.c b/rln.c
index f97b49034143fe66b20f3dd7b16b6e1ec805daee..1cbf9545efc88fbb39ad2d7f2fe6041fea454f59 100644 (file)
--- a/rln.c
+++ b/rln.c
@@ -1,6 +1,6 @@
 //
 // RLN - Reboot's Linker for the Atari Jaguar console system
-// Copyright (C) 199x, Allan K. Pratt, 2014-2015 Reboot & Friends
+// Copyright (C) 199x, Allan K. Pratt, 2014-2017 Reboot & Friends
 //
 
 #include "rln.h"
@@ -585,6 +585,7 @@ int RelocateSegment(struct OFILE * ofile, int flag)
        unsigned glblreloc;             // Global relocation flag
        unsigned absreloc;              // Absolute relocation flag
        unsigned relreloc;              // Relative relocation flag
+       unsigned wordreloc;             // Relocate word only flag
        unsigned swcond;                // Switch statement condition
        unsigned relocsize;             // Relocation record size
 
@@ -664,8 +665,9 @@ int RelocateSegment(struct OFILE * ofile, int flag)
                addr = GetLong(rptr);
                rflg = GetLong(rptr + 4);
                glblreloc = (rflg & 0x00000010 ? 1 : 0);// Set global relocation flag
-               absreloc = (rflg & 0x00000040 ? 1 : 0); // Set absolute relocation flag
-               relreloc = (rflg & 0x000000A0 ? 1 : 0); // Set relative relocation flag
+               absreloc  = (rflg & 0x00000040 ? 1 : 0); // Set absolute relocation flag
+               relreloc  = (rflg & 0x000000A0 ? 1 : 0); // Set relative relocation flag
+               wordreloc = (rflg & 0x00000002 ? 1 : 0); // Set word relocation flag
 
                // Additional processing required for global relocations
                if (glblreloc)
@@ -682,9 +684,10 @@ int RelocateSegment(struct OFILE * ofile, int flag)
                        newdata = GetLong(ost + ((ssidx - 1) * 12) + 8);
                }
 
-               // Obtain the existing long word segment data and flip words if the
-               // relocation flags indicate it relates to a RISC MOVEI instruction
-               olddata = GetLong(sptr + addr);
+               // Obtain the existing long word (or word) segment data and flip words
+               // if the relocation flags indicate it relates to a RISC MOVEI
+               // instruction
+               olddata = (wordreloc ? GetWord(sptr + addr) : GetLong(sptr + addr));
 
                if (rflg & 0x01)
                        olddata = _SWAPWORD(olddata);
@@ -734,7 +737,10 @@ int RelocateSegment(struct OFILE * ofile, int flag)
                        if (rflg & 0x01)
                                newdata = _SWAPWORD(newdata);
 
-                       PutLong(sptr + addr, newdata);
+                       if (wordreloc)
+                               PutWord(sptr + addr, newdata);
+                       else
+                               PutLong(sptr + addr, newdata);
                }
                else if (relreloc)
                {
@@ -2990,7 +2996,7 @@ void ShowVersion(void)
                "| |  | | | | |\n"
                "|_|  |_|_| |_|\n"
                "\nReboot's Linker for Atari Jaguar\n"
-               "Copyright (c) 199x Allan K. Pratt, 2014-2015 Reboot\n"
+               "Copyright (c) 199x Allan K. Pratt, 2014-2017 Reboot\n"
                "V%i.%i.%i %s (%s)\n\n", MAJOR, MINOR, PATCH, __DATE__, PLATFORM);
        }
 }
diff --git a/rln.h b/rln.h
index e9daf2a9bfb9d102d080366ece7a8793d3bf106f..34e8d6c3a020ffc7cdc6498a8af6d8c593a6d156 100644 (file)
--- a/rln.h
+++ b/rln.h
@@ -44,7 +44,7 @@
 
 #define MAJOR   1                      // Major version number
 #define MINOR   5                      // Minor version number
-#define PATCH   1                      // Patch release number
+#define PATCH   2                      // Patch release number
 
 #ifdef WIN32
 #define PLATFORM     "Win32"           // Release platform - Windows
@@ -90,22 +90,22 @@ struct OHEADER
        uint32_t bsize;
        uint32_t ssize;
        union {
-               struct {                                        // For .o 
+               struct {                                        // For .o
                        uint32_t tsize;                 // Text relocation size
                        uint32_t dsize;                 // Data relocation size
                        uint8_t reserved[12];
                } reloc;
-               struct {                                        // For .abs 
-                       uint32_t stksize;               // Unused 
-                       uint32_t tstart;                // Start of TEXT 
-                       uint32_t rbflag;                // -1 if no fixups at all 
-                       uint32_t dstart;                // Start of DATA 
+               struct {                                        // For .abs
+                       uint32_t stksize;               // Unused
+                       uint32_t tstart;                // Start of TEXT
+                       uint32_t rbflag;                // -1 if no fixups at all
+                       uint32_t dstart;                // Start of DATA
                        uint32_t bstart;                // Start of BSS
                } abs;
        } absrel;
-       uint8_t * ostbase;                              // Base of output symbol table 
+       uint8_t * ostbase;                              // Base of output symbol table
        uint32_t fsize;                                 // Length of fixups
-       uint8_t * fixups;                               // Start of fixups 
+       uint8_t * fixups;                               // Start of fixups
 };
 
 #define new_oheader()   (struct OHEADER *)malloc(sizeof(struct OHEADER))
@@ -118,7 +118,7 @@ struct ARHEADER
        uint8_t a_gid;
        uint16_t a_fimode;
        uint32_t a_fsize;
-       uint16_t reserved;                              // Two bytes zeroes btwn header & file 
+       uint16_t reserved;                              // Two bytes zeroes btwn header & file
 };
 
 #define new_arheader()  (struct ARHEADER *)malloc(sizeof(struct ARHEADER))
@@ -162,7 +162,7 @@ struct OFILE
 
 struct SYMREC
 {
-       uint8_t s_name[SYMLEN];                 // Including null terminator 
+       uint8_t s_name[SYMLEN];                 // Including null terminator
        uint16_t s_type;
        uint32_t s_value;
        struct SYMREC * s_next;