]> granicus.if.org Git - yasm/commitdiff
Enhance builtin bytecode_data to support embedded NULs in character strings.
authorPeter Johnson <peter@tortall.net>
Wed, 26 Oct 2005 03:22:44 +0000 (03:22 -0000)
committerPeter Johnson <peter@tortall.net>
Wed, 26 Oct 2005 03:22:44 +0000 (03:22 -0000)
While NASM doesn't allow this, GAS does.

While we're here, greatly clean up GAS data bytecode creation by no longer
building intermediate valparam list.

* bytecode.h (yasm_dv_create_string): Add length parameter.
(yasm_bc_create_data): Add append_zero parameter for new ability to append
a single ero byte after each data value.  This is used by the GAS .asciz
directive.
* bytecode.c (bytecode_data, ...): Implement the above.

* gas-bison.y (gas_define_strings, gas_define_data)
(gas_define_leb128): Remove; replace in usage with direct calls to bytecode
functions.  Add str, dataval, and datavalhead to parser union.  Add new
dirvals, which has valparams type, and change strvals and datavals to
datavals type.
* gas-token.re: Use new str type where STRING token is generated.

* nasm-bison.y: Add str type to union, and use for STRING token.
* nasm-token.re: Use new str type where STRING token is generated.

* coff-objfmt.c (win32_objfmt_directive): Adjust for updates to
bytecode_data.

* strzero.asm: Simple test for NUL in GAS string.

svn path=/trunk/yasm/; revision=1293

libyasm/bytecode.c
libyasm/bytecode.h
modules/objfmts/coff/coff-objfmt.c
modules/parsers/gas/gas-bison.y
modules/parsers/gas/gas-token.re
modules/parsers/gas/tests/Makefile.inc
modules/parsers/gas/tests/strzero.asm [new file with mode: 0644]
modules/parsers/gas/tests/strzero.errwarn [new file with mode: 0644]
modules/parsers/gas/tests/strzero.hex [new file with mode: 0644]
modules/parsers/nasm/nasm-bison.y
modules/parsers/nasm/nasm-token.re

index 742b6356c42ac4ec580c14d8263e60f0fc2a90eb..1abf415cb313d699c3d332dbdd7309f8c099bec4 100644 (file)
@@ -51,7 +51,10 @@ struct yasm_dataval {
 
     union {
        /*@only@*/ yasm_expr *expn;
-       /*@only@*/ char *str_val;
+       struct {
+           /*@only@*/ char *contents;
+           size_t len;
+       } str;
     } data;
 };
 
@@ -62,7 +65,10 @@ typedef struct bytecode_data {
     yasm_datavalhead datahead;
 
     /* final (converted) size of each element (in bytes) */
-    unsigned char size;
+    unsigned int size;
+
+    /* append a zero byte after each element? */
+    int append_zero;
 } bytecode_data;
 
 typedef struct bytecode_leb128 {
@@ -404,8 +410,8 @@ bc_data_print(const void *contents, FILE *f, int indent_level)
 {
     const bytecode_data *bc_data = (const bytecode_data *)contents;
     fprintf(f, "%*s_Data_\n", indent_level, "");
-    fprintf(f, "%*sFinal Element Size=%u\n", indent_level+1, "",
-           (unsigned int)bc_data->size);
+    fprintf(f, "%*sFinal Element Size=%u\n", indent_level+1, "", bc_data->size);
+    fprintf(f, "%*sAppend Zero=%i\n", indent_level+1, "", bc_data->append_zero);
     fprintf(f, "%*sElements:\n", indent_level+1, "");
     yasm_dvs_print(&bc_data->datahead, f, indent_level+2);
 }
@@ -427,12 +433,14 @@ bc_data_resolve(yasm_bytecode *bc, int save,
                bc->len += bc_data->size;
                break;
            case DV_STRING:
-               slen = strlen(dv->data.str_val);
+               slen = dv->data.str.len;
                /* find count, rounding up to nearest multiple of size */
                slen = (slen + bc_data->size - 1) / bc_data->size;
                bc->len += slen*bc_data->size;
                break;
        }
+       if (bc_data->append_zero)
+           bc->len++;
     }
 
     return YASM_BC_RESOLVE_MIN_LEN;
@@ -461,8 +469,8 @@ bc_data_tobytes(yasm_bytecode *bc, unsigned char **bufp, void *d,
                *bufp += bc_data->size;
                break;
            case DV_STRING:
-               slen = strlen(dv->data.str_val);
-               strncpy((char *)*bufp, dv->data.str_val, slen);
+               slen = dv->data.str.len;
+               memcpy(*bufp, dv->data.str.contents, slen);
                *bufp += slen;
                /* pad with 0's to nearest multiple of size */
                slen %= bc_data->size;
@@ -473,6 +481,8 @@ bc_data_tobytes(yasm_bytecode *bc, unsigned char **bufp, void *d,
                }
                break;
        }
+       if (bc_data->append_zero)
+           YASM_WRITE_8(*bufp, 0);
     }
 
     return 0;
@@ -480,12 +490,13 @@ bc_data_tobytes(yasm_bytecode *bc, unsigned char **bufp, void *d,
 
 yasm_bytecode *
 yasm_bc_create_data(yasm_datavalhead *datahead, unsigned int size,
-                   unsigned long line)
+                   int append_zero, unsigned long line)
 {
     bytecode_data *data = yasm_xmalloc(sizeof(bytecode_data));
 
     data->datahead = *datahead;
-    data->size = (unsigned char)size;
+    data->size = size;
+    data->append_zero = append_zero;
 
     return yasm_bc_create_common(&bc_data_callback, data, line);
 }
@@ -1415,12 +1426,13 @@ yasm_dv_create_expr(yasm_expr *expn)
 }
 
 yasm_dataval *
-yasm_dv_create_string(char *str_val)
+yasm_dv_create_string(char *contents, size_t len)
 {
     yasm_dataval *retval = yasm_xmalloc(sizeof(yasm_dataval));
 
     retval->type = DV_STRING;
-    retval->data.str_val = str_val;
+    retval->data.str.contents = contents;
+    retval->data.str.len = len;
 
     return retval;
 }
@@ -1438,7 +1450,7 @@ yasm_dvs_destroy(yasm_datavalhead *headp)
                yasm_expr_destroy(cur->data.expn);
                break;
            case DV_STRING:
-               yasm_xfree(cur->data.str_val);
+               yasm_xfree(cur->data.str.contents);
                break;
            default:
                break;
@@ -1475,8 +1487,10 @@ yasm_dvs_print(const yasm_datavalhead *head, FILE *f, int indent_level)
                fprintf(f, "\n");
                break;
            case DV_STRING:
-               fprintf(f, "%*sString=%s\n", indent_level, "",
-                       cur->data.str_val);
+               fprintf(f, "%*sLength=%lu\n", indent_level, "",
+                       (unsigned long)cur->data.str.len);
+               fprintf(f, "%*sString=\"%s\"\n", indent_level, "",
+                       cur->data.str.contents);
                break;
        }
     }
index e9adcfd89d33654bb5afac2a4cfccea06ac590c8..f9bca56ef94fd77f88f7b316f6a15483e27a7550 100644 (file)
@@ -135,11 +135,14 @@ void yasm_bc_set_multiple(yasm_bytecode *bc, /*@keep@*/ yasm_expr *e);
 /** Create a bytecode containing data value(s).
  * \param datahead     list of data values (kept, do not free)
  * \param size         storage size (in bytes) for each data value
+ * \param append_zero  append a single zero byte after each data value
+ *                     (if non-zero)
  * \param line         virtual line (from yasm_linemap)
  * \return Newly allocated bytecode.
  */
 /*@only@*/ yasm_bytecode *yasm_bc_create_data
-    (yasm_datavalhead *datahead, unsigned int size, unsigned long line);
+    (yasm_datavalhead *datahead, unsigned int size, int append_zero,
+     unsigned long line);
 
 /** Create a bytecode containing LEB128-encoded data value(s).
  * \param datahead     list of data values (kept, do not free)
@@ -336,7 +339,7 @@ yasm_dataval *yasm_dv_create_expr(/*@keep@*/ yasm_expr *expn);
  * \param str_val      string
  * \return Newly allocated data value.
  */
-yasm_dataval *yasm_dv_create_string(/*@keep@*/ char *str_val);
+yasm_dataval *yasm_dv_create_string(/*@keep@*/ char *contents, size_t len);
 
 /** Initialize a list of data values.
  * \param headp        list of data values
index a40a168b997956dcd1cc155d78e0e52533eaa539..15d530e6be8049be0ec2da3d1cacd8547f9a4ccb 100644 (file)
@@ -1393,10 +1393,12 @@ win32_objfmt_directive(yasm_objfmt *objfmt, const char *name,
        /* Add text as data bytecode */
        yasm_dvs_initialize(&dvs);
        yasm_dvs_append(&dvs,
-                       yasm_dv_create_string(yasm__xstrdup("-export:")));
-       yasm_dvs_append(&dvs, yasm_dv_create_string(yasm__xstrdup(vp->val)));
-       yasm_dvs_append(&dvs, yasm_dv_create_string(yasm__xstrdup(" ")));
-       yasm_section_bcs_append(sect, yasm_bc_create_data(&dvs, 1, line));
+                       yasm_dv_create_string(yasm__xstrdup("-export:"),
+                                             strlen("-export:")));
+       yasm_dvs_append(&dvs, yasm_dv_create_string(yasm__xstrdup(vp->val),
+                                                   strlen(vp->val)));
+       yasm_dvs_append(&dvs, yasm_dv_create_string(yasm__xstrdup(" "), 1));
+       yasm_section_bcs_append(sect, yasm_bc_create_data(&dvs, 1, 0, line));
 
        return 0;
     } else
index e29b21831bfe6db5c788cd0a255caaba3db7582d..1a6f7b19a69a4847a1c2d20a44bdc3d5d806e9f8 100644 (file)
@@ -52,14 +52,6 @@ static void gas_switch_section(yasm_parser_gas *parser_gas, char *name,
 static yasm_bytecode *gas_parser_align(yasm_parser_gas *parser_gas,
                                       yasm_valparamhead *valparams,
                                       int power2);
-static yasm_bytecode *gas_define_strings(yasm_parser_gas *parser_gas,
-                                        yasm_valparamhead *vps, int withzero);
-static yasm_bytecode *gas_define_data(yasm_parser_gas *parser_gas,
-                                     yasm_valparamhead *vps,
-                                     unsigned int size);
-static yasm_bytecode *gas_define_leb128(yasm_parser_gas *parser_gas,
-                                       yasm_valparamhead *vps,
-                                       int sign);
 static void gas_parser_directive
     (yasm_parser_gas *parser_gas, const char *name,
      yasm_valparamhead *valparams,
@@ -87,16 +79,22 @@ static void gas_parser_directive
     yasm_expr *exp;
     yasm_bytecode *bc;
     yasm_valparamhead valparams;
+    yasm_datavalhead datavals;
+    yasm_dataval *dv;
     struct {
        yasm_insn_operands operands;
        int num_operands;
     } insn_operands;
     yasm_insn_operand *insn_operand;
+    struct {
+       char *contents;
+       size_t len;
+    } str;
 }
 
 %token <intn> INTNUM
 %token <flt> FLTNUM
-%token <str_val> STRING
+%token <str> STRING
 %token <int_info> SIZE_OVERRIDE
 %token <int_info> DECLARE_DATA
 %token <int_info> RESERVE_SPACE
@@ -118,7 +116,8 @@ static void gas_parser_directive
 %type <ea> memaddr
 %type <exp> expr regmemexpr
 %type <sym> explabel
-%type <valparams> strvals datavals strvals2 datavals2
+%type <valparams> dirvals dirvals2
+%type <datavals> strvals datavals strvals2 datavals2
 %type <insn_operands> operands
 %type <insn_operand> operand
 
@@ -169,16 +168,16 @@ lineexp: instr
        define_label(parser_gas, $1, 0);
     }
     /* Alignment directives */
-    | DIR_ALIGN datavals2 {
+    | DIR_ALIGN dirvals2 {
        /* FIXME: Whether this is power-of-two or not depends on arch and
         * objfmt.
         */
        $$ = gas_parser_align(parser_gas, &$2, 0);
     }
-    | DIR_P2ALIGN datavals2 {
+    | DIR_P2ALIGN dirvals2 {
        $$ = gas_parser_align(parser_gas, &$2, 1);
     }
-    | DIR_BALIGN datavals2 {
+    | DIR_BALIGN dirvals2 {
        $$ = gas_parser_align(parser_gas, &$2, 0);
     }
     | DIR_ORG INTNUM {
@@ -257,52 +256,41 @@ lineexp: instr
     }
     /* Integer data definition directives */
     | DIR_ASCII strvals {
-       $$ = gas_define_strings(parser_gas, &$2, 0);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, 1, 0, cur_line);
     }
     | DIR_ASCIZ strvals {
-       $$ = gas_define_strings(parser_gas, &$2, 1);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, 1, 1, cur_line);
     }
     | DIR_BYTE datavals {
-       $$ = gas_define_data(parser_gas, &$2, 1);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, 1, 0, cur_line);
     }
     | DIR_SHORT datavals {
        /* TODO: This should depend on arch */
-       $$ = gas_define_data(parser_gas, &$2, 2);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, 2, 0, cur_line);
     }
     | DIR_WORD datavals {
-       $$ = gas_define_data(parser_gas, &$2,
-                            yasm_arch_wordsize(parser_gas->arch));
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, yasm_arch_wordsize(parser_gas->arch), 0,
+                                cur_line);
     }
     | DIR_INT datavals {
        /* TODO: This should depend on arch */
-       $$ = gas_define_data(parser_gas, &$2, 4);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, 4, 0, cur_line);
     }
     | DIR_VALUE datavals {
        /* XXX: At least on x86, this is two bytes */
-       $$ = gas_define_data(parser_gas, &$2, 2);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, 2, 0, cur_line);
     }
     | DIR_2BYTE datavals {
-       $$ = gas_define_data(parser_gas, &$2, 2);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, 2, 0, cur_line);
     }
     | DIR_4BYTE datavals {
-       $$ = gas_define_data(parser_gas, &$2, 4);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, 4, 0, cur_line);
     }
     | DIR_QUAD datavals {
-       $$ = gas_define_data(parser_gas, &$2, 8);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, 8, 0, cur_line);
     }
     | DIR_OCTA datavals {
-       $$ = gas_define_data(parser_gas, &$2, 16);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, 16, 0, cur_line);
     }
     | DIR_ZERO expr {
        yasm_datavalhead dvs;
@@ -310,30 +298,25 @@ lineexp: instr
        yasm_dvs_initialize(&dvs);
        yasm_dvs_append(&dvs, yasm_dv_create_expr(
            p_expr_new_ident(yasm_expr_int(yasm_intnum_create_uint(0)))));
-       $$ = yasm_bc_create_data(&dvs, 1, cur_line);
+       $$ = yasm_bc_create_data(&dvs, 1, 0, cur_line);
 
        yasm_bc_set_multiple($$, $2);
     }
     | DIR_SLEB128 datavals {
-       $$ = gas_define_leb128(parser_gas, &$2, 1);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_leb128(&$2, 1, cur_line);
     }
     | DIR_ULEB128 datavals {
-       $$ = gas_define_leb128(parser_gas, &$2, 0);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_leb128(&$2, 0, cur_line);
     }
     /* Floating point data definition directives */
     | DIR_FLOAT datavals {
-       $$ = gas_define_data(parser_gas, &$2, 4);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, 4, 0, cur_line);
     }
     | DIR_DOUBLE datavals {
-       $$ = gas_define_data(parser_gas, &$2, 8);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, 8, 0, cur_line);
     }
     | DIR_TFLOAT datavals {
-       $$ = gas_define_data(parser_gas, &$2, 10);
-       yasm_vps_delete(&$2);
+       $$ = yasm_bc_create_data(&$2, 10, 0, cur_line);
     }
     /* Empty space / fill data definition directives */
     | DIR_SKIP expr {
@@ -344,7 +327,7 @@ lineexp: instr
 
        yasm_dvs_initialize(&dvs);
        yasm_dvs_append(&dvs, yasm_dv_create_expr($4));
-       $$ = yasm_bc_create_data(&dvs, 1, cur_line);
+       $$ = yasm_bc_create_data(&dvs, 1, 0, cur_line);
 
        yasm_bc_set_multiple($$, $2);
     }
@@ -368,15 +351,15 @@ lineexp: instr
        $$ = NULL;
     }
     | DIR_SECTION label_id ',' STRING {
-       gas_switch_section(parser_gas, $2, $4, NULL, NULL);
+       gas_switch_section(parser_gas, $2, $4.contents, NULL, NULL);
        $$ = NULL;
     }
     | DIR_SECTION label_id ',' STRING ',' '@' label_id {
-       gas_switch_section(parser_gas, $2, $4, $7, NULL);
+       gas_switch_section(parser_gas, $2, $4.contents, $7, NULL);
        $$ = NULL;
     }
-    | DIR_SECTION label_id ',' STRING ',' '@' label_id ',' datavals {
-       gas_switch_section(parser_gas, $2, $4, $7, &$9);
+    | DIR_SECTION label_id ',' STRING ',' '@' label_id ',' dirvals {
+       gas_switch_section(parser_gas, $2, $4.contents, $7, &$9);
        $$ = NULL;
     }
     /* Other directives */
@@ -395,11 +378,10 @@ lineexp: instr
            yasm_dvs_append(&dvs, yasm_dv_create_expr(
                p_expr_new_ident(yasm_expr_int(yasm_intnum_create_uint(0)))));
            yasm_section_bcs_append(comment,
-                                   yasm_bc_create_data(&dvs, 1, cur_line));
+                                   yasm_bc_create_data(&dvs, 1, 0, cur_line));
        }
        yasm_section_bcs_append(comment,
-                               gas_define_strings(parser_gas, &$2, 1));
-       yasm_vps_delete(&$2);
+                               yasm_bc_create_data(&$2, 1, 1, cur_line));
        $$ = NULL;
     }
     | DIR_FILE INTNUM STRING {
@@ -446,7 +428,7 @@ lineexp: instr
        yasm_vps_delete(&vps);
        $$ = NULL;
     }
-    | DIR_ID datavals  {
+    | DIR_ID dirvals   {
        yasm__warning(YASM_WARN_GENERAL, cur_line,
                      N_("directive `%s' not recognized"), $1);
        $$ = (yasm_bytecode *)NULL;
@@ -507,48 +489,57 @@ instr: INSN               {
     }
 ;
 
-strvals: /* empty */   { yasm_vps_initialize(&$$); }
-    | strvals2
+dirvals: /* empty */   { yasm_vps_initialize(&$$); }
+    | dirvals2
 ;
 
-strvals2: STRING               {
-       yasm_valparam *vp = yasm_vp_create($1, NULL);
+dirvals2: expr                 {
+       yasm_valparam *vp = yasm_vp_create(NULL, $1);
        yasm_vps_initialize(&$$);
        yasm_vps_append(&$$, vp);
     }
-    | strvals2 ',' STRING      {
-       yasm_valparam *vp = yasm_vp_create($3, NULL);
+    | dirvals2 ',' expr        {
+       yasm_valparam *vp = yasm_vp_create(NULL, $3);
        yasm_vps_append(&$1, vp);
        $$ = $1;
     }
-    | strvals2 ',' ',' STRING  {
+    | dirvals2 ',' ',' expr    {
        yasm_valparam *vp = yasm_vp_create(NULL, NULL);
        yasm_vps_append(&$1, vp);
-       vp = yasm_vp_create($4, NULL);
+       vp = yasm_vp_create(NULL, $4);
        yasm_vps_append(&$1, vp);
        $$ = $1;
     }
 ;
 
-datavals: /* empty */  { yasm_vps_initialize(&$$); }
+strvals: /* empty */   { yasm_dvs_initialize(&$$); }
+    | strvals2
+;
+
+strvals2: STRING               {
+       yasm_dataval *dv = yasm_dv_create_string($1.contents, $1.len);
+       yasm_dvs_initialize(&$$);
+       yasm_dvs_append(&$$, dv);
+    }
+    | strvals2 ',' STRING      {
+       yasm_dataval *dv = yasm_dv_create_string($3.contents, $3.len);
+       yasm_dvs_append(&$1, dv);
+       $$ = $1;
+    }
+;
+
+datavals: /* empty */  { yasm_dvs_initialize(&$$); }
     | datavals2
 ;
 
 datavals2: expr                        {
-       yasm_valparam *vp = yasm_vp_create(NULL, $1);
-       yasm_vps_initialize(&$$);
-       yasm_vps_append(&$$, vp);
+       yasm_dataval *dv = yasm_dv_create_expr($1);
+       yasm_dvs_initialize(&$$);
+       yasm_dvs_append(&$$, dv);
     }
     | datavals2 ',' expr       {
-       yasm_valparam *vp = yasm_vp_create(NULL, $3);
-       yasm_vps_append(&$1, vp);
-       $$ = $1;
-    }
-    | datavals2 ',' ',' expr   {
-       yasm_valparam *vp = yasm_vp_create(NULL, NULL);
-       yasm_vps_append(&$1, vp);
-       vp = yasm_vp_create(NULL, $4);
-       yasm_vps_append(&$1, vp);
+       yasm_dataval *dv = yasm_dv_create_expr($3);
+       yasm_dvs_append(&$1, dv);
        $$ = $1;
     }
 ;
@@ -814,74 +805,6 @@ gas_parser_align(yasm_parser_gas *parser_gas, yasm_valparamhead *valparams,
                                cur_line);
 }
 
-static yasm_bytecode *
-gas_define_strings(yasm_parser_gas *parser_gas, yasm_valparamhead *vps,
-                  int withzero)
-{
-    if (yasm_vps_first(vps)) {
-       yasm_datavalhead dvs;
-       yasm_valparam *cur;
-
-       yasm_dvs_initialize(&dvs);
-       yasm_vps_foreach(cur, vps) {
-           if (!cur->val)
-               yasm__error(cur_line, N_("missing string value"));
-           else {
-               yasm_dvs_append(&dvs, yasm_dv_create_string(cur->val));
-               cur->val = NULL;
-               if (withzero)
-                   yasm_dvs_append(&dvs, yasm_dv_create_expr(
-                       p_expr_new_ident(yasm_expr_int(
-                           yasm_intnum_create_uint(0)))));
-           }
-       }
-       return yasm_bc_create_data(&dvs, 1, cur_line);
-    } else
-       return NULL;
-}
-
-static yasm_bytecode *
-gas_define_data(yasm_parser_gas *parser_gas, yasm_valparamhead *vps,
-               unsigned int size)
-{
-    if (yasm_vps_first(vps)) {
-       yasm_datavalhead dvs;
-       yasm_valparam *cur;
-
-       yasm_dvs_initialize(&dvs);
-       yasm_vps_foreach(cur, vps) {
-           if (!cur->param)
-               yasm__error(cur_line, N_("missing data value"));
-           else
-               yasm_dvs_append(&dvs, yasm_dv_create_expr(cur->param));
-           cur->param = NULL;
-       }
-       return yasm_bc_create_data(&dvs, size, cur_line);
-    } else
-       return NULL;
-}
-
-static yasm_bytecode *
-gas_define_leb128(yasm_parser_gas *parser_gas, yasm_valparamhead *vps,
-                 int sign)
-{
-    if (yasm_vps_first(vps)) {
-       yasm_datavalhead dvs;
-       yasm_valparam *cur;
-
-       yasm_dvs_initialize(&dvs);
-       yasm_vps_foreach(cur, vps) {
-           if (!cur->param)
-               yasm__error(cur_line, N_("missing data value"));
-           else
-               yasm_dvs_append(&dvs, yasm_dv_create_expr(cur->param));
-           cur->param = NULL;
-       }
-       return yasm_bc_create_leb128(&dvs, sign, cur_line);
-    } else
-       return NULL;
-}
-
 static void
 gas_parser_directive(yasm_parser_gas *parser_gas, const char *name,
                      yasm_valparamhead *valparams,
index 876b95ca37293f5ce763c6fddb7c0eb582719b5c..98db9472ec78b2f54752e85caf8d8d7f96ddffca 100644 (file)
@@ -494,7 +494,8 @@ stringconst_scan:
 
        dquot   {
            strbuf_append(count, cursor, s, cur_line, '\0');
-           lvalp->str_val = strbuf;
+           lvalp->str.contents = strbuf;
+           lvalp->str.len = count;
            RETURN(STRING);
        }
 
index 2a54bcc7145e7a32f405c303cfa6bf797e628f04..484d60eb18a3afcefa69b575a062ff7718f7b880 100644 (file)
@@ -26,6 +26,9 @@ EXTRA_DIST += modules/parsers/gas/tests/reggroup-err.errwarn
 EXTRA_DIST += modules/parsers/gas/tests/reggroup.asm
 EXTRA_DIST += modules/parsers/gas/tests/reggroup.errwarn
 EXTRA_DIST += modules/parsers/gas/tests/reggroup.hex
+EXTRA_DIST += modules/parsers/gas/tests/strzero.asm
+EXTRA_DIST += modules/parsers/gas/tests/strzero.errwarn
+EXTRA_DIST += modules/parsers/gas/tests/strzero.hex
 EXTRA_DIST += modules/parsers/gas/tests/varinsn.asm
 EXTRA_DIST += modules/parsers/gas/tests/varinsn.errwarn
 EXTRA_DIST += modules/parsers/gas/tests/varinsn.hex
diff --git a/modules/parsers/gas/tests/strzero.asm b/modules/parsers/gas/tests/strzero.asm
new file mode 100644 (file)
index 0000000..b23a358
--- /dev/null
@@ -0,0 +1 @@
+.ascii "abc\000def"
diff --git a/modules/parsers/gas/tests/strzero.errwarn b/modules/parsers/gas/tests/strzero.errwarn
new file mode 100644 (file)
index 0000000..e69de29
diff --git a/modules/parsers/gas/tests/strzero.hex b/modules/parsers/gas/tests/strzero.hex
new file mode 100644 (file)
index 0000000..4cc7a10
--- /dev/null
@@ -0,0 +1,360 @@
+7f 
+45 
+4c 
+46 
+01 
+01 
+01 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+01 
+00 
+03 
+00 
+01 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+a0 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+34 
+00 
+00 
+00 
+00 
+00 
+28 
+00 
+05 
+00 
+01 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+61 
+62 
+63 
+00 
+64 
+65 
+66 
+00 
+00 
+2e 
+74 
+65 
+78 
+74 
+00 
+2e 
+73 
+74 
+72 
+74 
+61 
+62 
+00 
+2e 
+73 
+79 
+6d 
+74 
+61 
+62 
+00 
+2e 
+73 
+68 
+73 
+74 
+72 
+74 
+61 
+62 
+00 
+00 
+00 
+00 
+00 
+2d 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+01 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+04 
+00 
+f1 
+ff 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+03 
+00 
+04 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+17 
+00 
+00 
+00 
+03 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+48 
+00 
+00 
+00 
+21 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+07 
+00 
+00 
+00 
+03 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+6c 
+00 
+00 
+00 
+03 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+0f 
+00 
+00 
+00 
+02 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+70 
+00 
+00 
+00 
+30 
+00 
+00 
+00 
+02 
+00 
+00 
+00 
+03 
+00 
+00 
+00 
+04 
+00 
+00 
+00 
+10 
+00 
+00 
+00 
+01 
+00 
+00 
+00 
+01 
+00 
+00 
+00 
+06 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+40 
+00 
+00 
+00 
+07 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
+10 
+00 
+00 
+00 
+00 
+00 
+00 
+00 
index adf6c943cf512620e4347dfc837ff82ac76ec173..853f68c88fc279c1e0be552e47a078c815c02551 100644 (file)
@@ -82,11 +82,16 @@ static void define_label(yasm_parser_nasm *parser_nasm, /*@only@*/ char *name,
        char *name;
        int local;
     } label;
+    struct {
+       char *contents;
+       size_t len;
+    } str;
 }
 
 %token <intn> INTNUM
 %token <flt> FLTNUM
-%token <str_val> DIRECTIVE_NAME STRING FILENAME
+%token <str_val> DIRECTIVE_NAME FILENAME
+%token <str> STRING
 %token <int_info> SIZE_OVERRIDE
 %token <int_info> DECLARE_DATA
 %token <int_info> RESERVE_SPACE
@@ -191,25 +196,25 @@ lineexp: exp
 
 exp: instr
     | DECLARE_DATA datavals            {
-       $$ = yasm_bc_create_data(&$2, $1, cur_line);
+       $$ = yasm_bc_create_data(&$2, $1, 0, cur_line);
     }
     | RESERVE_SPACE expr               {
        $$ = yasm_bc_create_reserve($2, $1, cur_line);
     }
     | INCBIN STRING                    {
-       $$ = yasm_bc_create_incbin($2, NULL, NULL, cur_line);
+       $$ = yasm_bc_create_incbin($2.contents, NULL, NULL, cur_line);
     }
     | INCBIN STRING ','                        {
-       $$ = yasm_bc_create_incbin($2, NULL, NULL, cur_line);
+       $$ = yasm_bc_create_incbin($2.contents, NULL, NULL, cur_line);
     }
     | INCBIN STRING ',' expr           {
-       $$ = yasm_bc_create_incbin($2, $4, NULL, cur_line);
+       $$ = yasm_bc_create_incbin($2.contents, $4, NULL, cur_line);
     }
     | INCBIN STRING ',' expr ','       {
-       $$ = yasm_bc_create_incbin($2, $4, NULL, cur_line);
+       $$ = yasm_bc_create_incbin($2.contents, $4, NULL, cur_line);
     }
     | INCBIN STRING ',' expr ',' expr  {
-       $$ = yasm_bc_create_incbin($2, $4, $6, cur_line);
+       $$ = yasm_bc_create_incbin($2.contents, $4, $6, cur_line);
     }
 ;
 
@@ -243,7 +248,9 @@ datavals: dataval       {
 ;
 
 dataval: dvexpr                { $$ = yasm_dv_create_expr($1); }
-    | STRING           { $$ = yasm_dv_create_string($1); }
+    | STRING           {
+       $$ = yasm_dv_create_string($1.contents, $1.len);
+    }
     | error            {
        yasm__error(cur_line, N_("expression syntax error"));
        $$ = (yasm_dataval *)NULL;
@@ -309,7 +316,7 @@ directive_valparam: direxpr {
            $$ = yasm_vp_create(NULL, $1);
        }
     }
-    | STRING                   { $$ = yasm_vp_create($1, NULL); }
+    | STRING                   { $$ = yasm_vp_create($1.contents, NULL); }
     | ID '=' direxpr           {
        yasm_expr__traverse_leaves_in($3, parser_nasm, fix_directive_symrec);
        $$ = yasm_vp_create($1, $3);
@@ -424,8 +431,8 @@ expr: INTNUM                { $$ = p_expr_new_ident(yasm_expr_int($1)); }
     | REG              { $$ = p_expr_new_ident(yasm_expr_reg($1[0])); }
     | STRING           {
        $$ = p_expr_new_ident(yasm_expr_int(
-           yasm_intnum_create_charconst_nasm($1, cur_line)));
-       yasm_xfree($1);
+           yasm_intnum_create_charconst_nasm($1.contents, cur_line)));
+       yasm_xfree($1.contents);
     }
     | explabel         { $$ = p_expr_new_ident(yasm_expr_sym($1)); }
     /*| expr '||' expr { $$ = p_expr_new_tree($1, YASM_EXPR_LOR, $3); }*/
index d7a33275f49f56cef5ed78e1fda12e41b7a95281..41a1377a9a0fb9b0b180a3df3b7d26e471f6772a 100644 (file)
@@ -539,7 +539,8 @@ stringconst_scan:
            else
                yasm__error(cur_line, N_("unterminated string"));
            strbuf[count] = '\0';
-           lvalp->str_val = strbuf;
+           lvalp->str.contents = strbuf;
+           lvalp->str.len = count;
            if (parser_nasm->save_input && cursor != s->eof)
                cursor = save_line(parser_nasm, cursor);
            RETURN(STRING);
@@ -548,7 +549,8 @@ stringconst_scan:
        any     {
            if (s->tok[0] == endch) {
                strbuf[count] = '\0';
-               lvalp->str_val = strbuf;
+               lvalp->str.contents = strbuf;
+               lvalp->str.len = count;
                RETURN(STRING);
            }