diff label.c @ 4:0990d9322fc8

Implement address-ranged labels. Breaks compatibility of label files.
author Matti Hamalainen <ccr@tnsp.org>
date Wed, 25 Feb 2015 04:15:07 +0200
parents ec2f8f6f1dc9
children 122134900c0e
line wrap: on
line diff
--- a/label.c	Wed Feb 25 04:13:08 2015 +0200
+++ b/label.c	Wed Feb 25 04:15:07 2015 +0200
@@ -40,19 +40,13 @@
 #include "opcodes.h"
 
 label *labeltable;
-char defaultlabel[6];
+char defaultlabel[512];
 unsigned numLabels = 0;
 
 
-void AddLabel (ADDR_T address, char *name)
+void AddLabel(ADDR_T address, char *name, int is_range, ADDR_T len)
 {
-  label *entry;
-  char *buffer;
-
-  if (!((buffer = malloc (strlen (name) + 1))))
-    return;
-
-  entry = numLabels ?
+  label * entry = numLabels ?
     realloc (labeltable, (numLabels + 1) * sizeof *entry) :
     malloc (sizeof *entry);
 
@@ -62,31 +56,67 @@
   entry = &labeltable[numLabels++];
 
   entry->address = address;
-  entry->name = buffer;
-  while ((*buffer++ = *name++));
+  entry->name = strdup(name);
+  entry->is_range = is_range;
+  entry->len = len;
 }
 
-
-char *Label (ADDR_T address, int admode)
+int IsInsideRegion(ADDR_T address)
 {
   label *entry;
 
-  if (!IsLabeled (address)) {
+  for (entry = &labeltable[numLabels]; entry-- > labeltable;)
+  {
+    int offs = address - entry->address;
+    if (entry->is_range && offs > 0 && offs < entry->len)
+      return TRUE;
+  }
+  return FALSE;
+}
+
 
-	/* dirty kludge to allow zero page stuff to still work. this sometimes
-		guesses wrong */
-	if (admode == zp)
-    		sprintf (defaultlabel, "$%02x", address);
-	else
-    		sprintf (defaultlabel, "$%04x", address);
+char *Label(ADDR_T address, int admode, int allow_range)
+{
+  label *entry;
+  int match = 0;
+
+  if (!IsLabeled (address)) {
+    // dirty kludge to allow zero page stuff to still work. this sometimes
+    // guesses wrong
+    if (admode == zp)
+      snprintf(defaultlabel, sizeof(defaultlabel), "$%02x", address);
+    else
+      snprintf(defaultlabel, sizeof(defaultlabel), "$%04x", address);
+
     return defaultlabel;
   }
 
   for (entry = &labeltable[numLabels]; entry-- > labeltable;)
+  {
+    int offs = address - entry->address;
+
     if (entry->address == address)
       return entry->name;
 
-  sprintf (defaultlabel, "l%x", address);
+    if (entry->is_range && offs >= 0 && offs < entry->len)
+    {
+      match = 1;
+      if (allow_range)
+      {
+        snprintf(defaultlabel, sizeof(defaultlabel),
+          (offs < 16) ? "%s + %d" : "%s + $%x",
+          entry->name, offs);
+        return defaultlabel;
+      }
+      else
+        break;
+    }
+  }
+
+  if (match)
+    snprintf(defaultlabel, sizeof(defaultlabel), "XXX_%x", address);
+  else
+    snprintf(defaultlabel, sizeof(defaultlabel), "l_%x", address);
 
   return defaultlabel;
 }