This is the mail archive of the binutils@sourceware.org mailing list for the binutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

ongoing work on TI CodeComposer Studio assembly support


Hi,

   I'm adding support for the assembly syntax of the TI CodeComposer Studio
(see -mccs flag in the patch). This is an ongoing work, which already
assemblies most of our legacy hand-written assembly sources.

I'd like to know: in CCS, all symbols are not exported by default, as explained
in the manual:

    The assembler generates an entry in the symbol table for each .ref, .def,
    or .global directive in Section 2.6.2). The assembler also creates special
    symbols that point to the beginning of each section.
    The assembler does not usually create symbol table entries for any symbols
    other than those described above, because the linker does not use them. For
    example, labels (Section 4.7.2) are not included in the symbol table unless
    they are declared with the .global directive.

>From this, I have two options here regarding the behavior of the assembler in
the TI CCS compatibility mode:

 1) do nothing, and make the ".def" TI directive equivalent to ".global", as I
    currently do in the attached patch. This is currently working.

 2) by default, make all labels private as if they would be .Lxxx (I originally
    did this, and is in the patch within the #ifdef DFG directives, but made
    no difference) unless they are marked with the ".def" directive.

Please let me know if I'm in the good path by following the option 1 (in which
case all the DFG code will be gone).

Sorry for the lack of test cases and CHANGELOG, but I would really
appreciate some early feedback of the patch.


Thanks!

  Daniel.

-- 

Daniel F. Gutson
Chief Engineering Officer, SPD


San Lorenzo 47, 3rd Floor, Office 5
Córdoba, Argentina

Phone: +54 351 4217888 / +54 351 4218211

Skype: dgutson
diff -Naur binutils-2.23.52-original/gas/as.h binutils-2.23.52/gas/as.h
--- binutils-2.23.52-original/gas/as.h	2014-02-05 16:40:52.797157053 -0300
+++ binutils-2.23.52/gas/as.h	2014-02-05 18:44:27.109464433 -0300
@@ -615,6 +615,10 @@
 #define NO_PSEUDO_DOT 0
 #endif
 
+#ifndef OVERRIDE_LOCAL_LABEL_TEST
+#define OVERRIDE_LOCAL_LABEL_TEST(sym_name) FALSE
+#endif
+
 #ifndef TEXT_SECTION_NAME
 #define TEXT_SECTION_NAME	".text"
 #define DATA_SECTION_NAME	".data"
diff -Naur binutils-2.23.52-original/gas/config/tc-arm.c binutils-2.23.52/gas/config/tc-arm.c
--- binutils-2.23.52-original/gas/config/tc-arm.c	2014-02-05 16:41:16.309158028 -0300
+++ binutils-2.23.52/gas/config/tc-arm.c	2014-02-06 17:39:35.877659569 -0300
@@ -137,6 +137,9 @@
 /* Warn on using deprecated features.  */
 static int warn_on_deprecated = TRUE;
 
+/* Understand CodeComposer Studio assembly syntax.  */
+int codecomposer_syntax = FALSE;
+
 
 /* Variables that we set while parsing command-line options.  Once all
    options have been read we re-process these values to set the real
@@ -795,6 +798,28 @@
 /* Pointer to a linked list of literal pools.  */
 literal_pool * list_of_pools = NULL;
 
+#ifdef DFG
+/*  List of symbols to export. This is for CodeComposer Studio compatibility
+    since all symbols are locals, unless a .def pseudo-op is specified.
+    This list holds those symbols that shall be exported.  */
+typedef struct symbol_to_export
+{
+  const char * symbol_name;
+  struct symbol_to_export * next;
+} symbol_to_export;
+
+static symbol_to_export * list_of_symbols_to_export = NULL;
+#endif
+
+typedef enum asmfunc_states
+{
+  OUTSIDE_ASMFUNC,
+  WAITING_ASMFUNC_NAME,
+  WAITING_ENDASMFUNC
+} asmfunc_states;
+
+static asmfunc_states asmfunc_state = OUTSIDE_ASMFUNC;
+
 #ifdef OBJ_ELF
 #  define now_it seg_info (now_seg)->tc_segment_info_data.current_it
 #else
@@ -853,7 +878,7 @@
 
 /* This array holds the chars that always start a comment.  If the
    pre-processor is disabled, these aren't very useful.	 */
-const char comment_chars[] = "@";
+char comment_chars[] = "@";
 
 /* This array holds the chars that only start a comment at the beginning of
    a line.  If the line seems to have the form '# 123 filename'
@@ -862,9 +887,9 @@
    first line of the input file.  This is because the compiler outputs
    #NO_APP at the beginning of its output.  */
 /* Also note that comments like this one will always work.  */
-const char line_comment_chars[] = "#";
+char line_comment_chars[] = "#";
 
-const char line_separator_chars[] = ";";
+char line_separator_chars[] = ";";
 
 /* Chars that can be used to separate mant
    from exp in floating point numbers.	*/
@@ -3012,6 +3037,160 @@
   demand_empty_rest_of_line ();
 }
 
+/*  .ref  (for CodeComposer Studio syntax only).  */
+static void
+s_ccs_ref (int unused ATTRIBUTE_UNUSED)
+{
+  if (codecomposer_syntax)
+    ignore_rest_of_line ();
+  else
+    as_bad (_(".ref pseudo-op only available with -mccs flag."));
+}
+
+/*  If name is not NULL, then it is used for marking the beginning of a
+    function, wherease if it is NULL then it means the function end.  */
+static void
+asmfunc_debug (const char * name)
+{
+  static const char * last_name = NULL;
+
+  if (name != NULL)
+    {
+      gas_assert (last_name == NULL);
+      last_name = name;
+
+      if (debug_type == DEBUG_STABS)
+	      stabs_generate_asm_func (name, name);
+
+    }
+  else
+    {
+      gas_assert (last_name != NULL);
+
+      if (debug_type == DEBUG_STABS)
+        stabs_generate_asm_endfunc (last_name, last_name);
+
+      last_name = NULL;
+    }
+}
+
+static void
+s_ccs_asmfunc (int unused ATTRIBUTE_UNUSED)
+{
+  if (codecomposer_syntax)
+  {
+    switch (asmfunc_state)
+      {
+      case OUTSIDE_ASMFUNC:
+        asmfunc_state = WAITING_ASMFUNC_NAME;
+        break;
+
+      case WAITING_ASMFUNC_NAME:
+        as_bad (_(".asmfunc repeated."));
+        break;
+
+      case WAITING_ENDASMFUNC:
+        as_bad (_(".asmfunc without function."));
+        break;
+      }
+    demand_empty_rest_of_line ();
+  }
+  else
+    as_bad (_(".asmfunc pseudo-op only available with -mccs flag."));
+}
+
+#ifdef DFG
+bfd_boolean arm_local_label_p(const char *sym_name)
+{
+  if (codecomposer_syntax && FALSE) /* DFG */
+    {
+      bfd_boolean found = FALSE;
+
+      /*  Find the sym_name in the list_of_symbols_to_export.  */
+      symbol_to_export * symbol_node = list_of_symbols_to_export;
+
+      while (symbol_node != NULL && ! found)
+        {
+          found = (strcmp (symbol_node->symbol_name, sym_name) == 0);
+          symbol_node = symbol_node->next;
+        }
+
+      return ! found;
+    }
+  else
+    return FALSE;
+}
+#endif
+
+static void
+s_ccs_endasmfunc (int unused ATTRIBUTE_UNUSED)
+{
+  if (codecomposer_syntax)
+  {
+    switch (asmfunc_state)
+      {
+      case OUTSIDE_ASMFUNC:
+        as_bad (_(".endasmfunc without a .asmfunc."));
+        break;
+
+      case WAITING_ASMFUNC_NAME:
+        as_bad (_(".endasmfunc without function."));
+        break;
+
+      case WAITING_ENDASMFUNC:
+        asmfunc_state = OUTSIDE_ASMFUNC;
+        asmfunc_debug (NULL);
+        break;
+      }
+    demand_empty_rest_of_line ();
+  }
+  else
+    as_bad (_(".endasmfunc pseudo-op only available with -mccs flag."));
+}
+
+static void
+s_ccs_def (int unused /*ATTRIBUTE_UNUSED*/)
+{
+  if (codecomposer_syntax)
+    {
+      s_globl (unused);
+#ifdef DFG
+      char *name;
+      /* Add the symbol name to list_of_symbols_to_export.  */
+
+      SKIP_WHITESPACE ();
+      name = input_line_pointer;
+      if (name != '\0')
+        {
+          const char delim = get_symbol_end ();
+          name = xstrdup (name);
+          *input_line_pointer = delim;
+          demand_empty_rest_of_line ();
+
+          symbol_to_export *new_symbol_node = (symbol_to_export *) xmalloc (
+            sizeof (symbol_to_export));
+
+          new_symbol_node->next = NULL;
+          new_symbol_node->symbol_name = name;
+
+          if (list_of_symbols_to_export == NULL)
+            list_of_symbols_to_export = new_symbol_node;
+          else
+            {
+              symbol_to_export *last = list_of_symbols_to_export;
+              while (last->next != NULL)
+                last = last->next;
+              last->next = new_symbol_node;
+            }
+        }
+      else
+        as_bad (_("missing symbol name after .def pseudo-op."));
+#endif
+    }
+  else
+    as_bad (_(".def pseudo-op only available with -mccs flag."));
+}
+
 /* Directives: Literal pools.  */
 
 static literal_pool *
@@ -3128,6 +3307,41 @@
   return SUCCESS;
 }
 
+#ifdef DFG
+void
+tc_arm_symbol_new_hook(symbolS * symbolP ATTRIBUTE_UNUSED)
+{
+/*  printf ("DFG: new symbol %s\n", S_GET_NAME (symbolP));*/
+}
+#endif
+
+bfd_boolean
+tc_start_label_without_colon (char unused1 ATTRIBUTE_UNUSED, const char * rest)
+{
+  bfd_boolean ret = TRUE;
+
+  if (codecomposer_syntax && asmfunc_state == WAITING_ASMFUNC_NAME)
+  {
+    const char *label = rest;
+
+    while (!is_end_of_line[(int) label[-1]])
+	    --label;
+
+    if (*label == '.')
+	    {
+	      as_bad (_("Invalid label '%s'"), label);
+	      ret = FALSE;
+	    }
+
+    asmfunc_debug (label);
+
+    asmfunc_state = WAITING_ENDASMFUNC;
+  }
+
+  return ret;
+}
+
+
 /* Can't use symbol_new here, so have to create a symbol and then at
    a later date assign it a value. Thats what these functions do.  */
 
@@ -4477,6 +4691,12 @@
 #ifdef TE_PE
   {"secrel32", pe_directive_secrel, 0},
 #endif
+  /* These are for compatibility with CodeComposer Studio.  */
+  {"ref", s_ccs_ref, 0},
+  {"def", s_ccs_def, 0},
+  {"asmfunc", s_ccs_asmfunc, 0},
+  {"endasmfunc", s_ccs_endasmfunc, 0},
+
   { 0, 0, 0 }
 };
 
@@ -23759,6 +23979,7 @@
   {"mbig-endian", N_("assemble for big-endian"), &target_big_endian, 1, NULL},
   {"mlittle-endian", N_("assemble for little-endian"), &target_big_endian, 0,
    NULL},
+  {"mapcs-stack-check", N_("use stack size checking"), NULL, 0, NULL},
 
   /* These are recognized by the assembler, but have no affect on code.	 */
   {"mapcs-frame", N_("use frame pointer"), NULL, 0, NULL},
@@ -24508,6 +24729,15 @@
   return ret;
 }
 
+static bfd_boolean
+arm_ccs_mode (char * unused ATTRIBUTE_UNUSED)
+{
+  codecomposer_syntax = TRUE;
+  comment_chars[0] = ';';
+  line_separator_chars[0] = 0;
+	return TRUE;
+}
+
 struct arm_long_option_table arm_long_opts[] =
 {
   {"mcpu=", N_("<cpu name>\t  assemble for CPU <cpu name>"),
@@ -24524,6 +24754,8 @@
 #endif
   {"mimplicit-it=", N_("<mode>\t  controls implicit insertion of IT instructions"),
    arm_parse_it_mode, NULL},
+  {"mccs", N_("\t\t\t  TI CodeComposer Studio syntax compatibility mode"),
+   arm_ccs_mode, NULL},
   {NULL, NULL, 0, NULL}
 };
 
diff -Naur binutils-2.23.52-original/gas/config/tc-arm.h binutils-2.23.52/gas/config/tc-arm.h
--- binutils-2.23.52-original/gas/config/tc-arm.h	2014-02-05 16:41:16.389158031 -0300
+++ binutils-2.23.52/gas/config/tc-arm.h	2014-02-06 13:40:34.785250285 -0300
@@ -82,9 +82,18 @@
 /* We support double slash line-comments for compatibility with the ARM AArch64 Assembler.  */
 #define DOUBLESLASH_LINE_COMMENTS
 
+/* We conditionally support labels without colon.  */
+#define LABELS_WITHOUT_COLONS codecomposer_syntax
+extern int codecomposer_syntax;
+
 #define tc_symbol_chars arm_symbol_chars
 extern const char arm_symbol_chars[];
 
+#ifdef DFG
+#define OVERRIDE_LOCAL_LABEL_TEST(sym_name) arm_local_label_p(sym_name)
+extern bfd_boolean arm_local_label_p(const char *sym_name);
+#endif
+
 #define TC_FORCE_RELOCATION(FIX) arm_force_relocation (FIX)
 
 extern unsigned int arm_frag_max_var (struct frag *);
@@ -101,6 +110,14 @@
 
 #define md_start_line_hook() arm_start_line_hook ()
 
+#ifdef DFG
+#define tc_symbol_new_hook(S) tc_arm_symbol_new_hook(S)
+extern void tc_arm_symbol_new_hook(symbolS *symbolP);
+#endif
+
+#define TC_START_LABEL_WITHOUT_COLON(c, l)  tc_start_label_without_colon (c, l)
+extern bfd_boolean tc_start_label_without_colon (char c, const char * l);
+
 #define tc_frob_label(S) arm_frob_label (S)
 
 /* We also need to mark assembler created symbols:  */
diff -Naur binutils-2.23.52-original/gas/config/tc-h8300.c binutils-2.23.52/gas/config/tc-h8300.c
--- binutils-2.23.52-original/gas/config/tc-h8300.c	2014-02-05 16:41:15.729158004 -0300
+++ binutils-2.23.52/gas/config/tc-h8300.c	2014-02-06 09:34:43.608623410 -0300
@@ -33,9 +33,9 @@
 #include "elf/h8.h"
 #endif
 
-const char comment_chars[] = ";";
-const char line_comment_chars[] = "#";
-const char line_separator_chars[] = "";
+char comment_chars[] = ";";
+char line_comment_chars[] = "#";
+char line_separator_chars[] = "";
 
 static void sbranch (int);
 static void h8300hmode (int);
diff -Naur binutils-2.23.52-original/gas/read.h binutils-2.23.52/gas/read.h
--- binutils-2.23.52-original/gas/read.h	2014-02-05 16:41:17.981158097 -0300
+++ binutils-2.23.52/gas/read.h	2014-02-06 09:30:45.708635440 -0300
@@ -61,9 +61,9 @@
 extern int target_big_endian;
 
 /* These are initialized by the CPU specific target files (tc-*.c).  */
-extern const char comment_chars[];
-extern const char line_comment_chars[];
-extern const char line_separator_chars[];
+extern char comment_chars[];
+extern char line_comment_chars[];
+extern char line_separator_chars[];
 
 /* Table of -I directories.  */
 extern char **include_dirs;
diff -Naur binutils-2.23.52-original/gas/symbols.c binutils-2.23.52/gas/symbols.c
--- binutils-2.23.52-original/gas/symbols.c	2014-02-05 16:41:18.041158100 -0300
+++ binutils-2.23.52/gas/symbols.c	2014-02-06 13:41:22.493250705 -0300
@@ -441,7 +441,14 @@
 	}
 
     }
-  else if (! flag_keep_locals && bfd_is_local_label_name (stdoutput, sym_name))
+#ifdef DFG
+  else if (! flag_keep_locals
+       && (bfd_is_local_label_name (stdoutput, sym_name)
+           || OVERRIDE_LOCAL_LABEL_TEST(sym_name)))
+#else
+  else if (! flag_keep_locals
+       && (bfd_is_local_label_name (stdoutput, sym_name)))
+#endif
     {
       symbolP = (symbolS *) local_symbol_make (sym_name, now_seg,
 					       (valueT) frag_now_fix (),

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]