From d6f53b25823984c85471b4d6f00749312d2016f5 Mon Sep 17 00:00:00 2001 From: steve Date: Fri, 7 Jan 2000 03:45:49 +0000 Subject: [PATCH] Initial support for signed constants. --- lexor.lex | 104 ++++++++++++++++++++++++++++++++++++++++++----------- verinum.cc | 22 +++++++----- verinum.h | 9 ++++- 3 files changed, 106 insertions(+), 29 deletions(-) diff --git a/lexor.lex b/lexor.lex index 92a7d641b..19da91ddf 100644 --- a/lexor.lex +++ b/lexor.lex @@ -19,7 +19,7 @@ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA */ #if !defined(WINNT) -#ident "$Id: lexor.lex,v 1.40 1999/12/31 03:24:30 steve Exp $" +#ident "$Id: lexor.lex,v 1.41 2000/01/07 03:45:49 steve Exp $" #endif //# define YYSTYPE lexval @@ -160,26 +160,26 @@ W [ \t\b\f\r]+ yylval.text = strdup(cp); return PORTNAME; } -[0-9][0-9_]*[ \t]*\'[dD][ \t]*[0-9][0-9_]* { +[0-9][0-9_]*[ \t]*\'[sS]?[dD][ \t]*[0-9][0-9_]* { yylval.number = make_sized_dec(yytext); return NUMBER; } -[0-9][0-9_]*[ \t]*\'[bB][ \t]*[0-1xzXZ_\?]+ { +[0-9][0-9_]*[ \t]*\'[sS]?[bB][ \t]*[0-1xzXZ_\?]+ { yylval.number = make_sized_binary(yytext); return NUMBER; } -[0-9][0-9_]*[ \t]*\'[oO][ \t]*[0-7xzXZ_\?]+ { +[0-9][0-9_]*[ \t]*\'[sS]?[oO][ \t]*[0-7xzXZ_\?]+ { yylval.number = make_sized_octal(yytext); return NUMBER; } -[0-9][0-9_]*[ \t]*\'[hH][ \t]*[0-9a-fA-FxzXZ_\?]+ { +[0-9][0-9_]*[ \t]*\'[sS]?[hH][ \t]*[0-9a-fA-FxzXZ_\?]+ { yylval.number = make_sized_hex(yytext); return NUMBER; } -\'d[ \t]*[0-9][0-9_]* { yylval.number = make_unsized_dec(yytext); - return NUMBER; } -\'[bB][ \t]*[0-1xzXZ_\?]+ { yylval.number = make_unsized_binary(yytext); +\'[sS]?[dD][ \t]*[0-9][0-9_]* { yylval.number = make_unsized_dec(yytext); + return NUMBER; } +\'[sS]?[bB][ \t]*[0-1xzXZ_\?]+ { yylval.number = make_unsized_binary(yytext); return NUMBER; } -\'[oO][ \t]*[0-7xzXZ_\?]+ { yylval.number = make_unsized_octal(yytext); +\'[sS]?[oO][ \t]*[0-7xzXZ_\?]+ { yylval.number = make_unsized_octal(yytext); return NUMBER; } -\'[hH][ \t]*[0-9a-fA-FxzXZ_\?]+ { yylval.number = make_unsized_hex(yytext); +\'[sS]?[hH][ \t]*[0-9a-fA-FxzXZ_\?]+ { yylval.number = make_unsized_hex(yytext); return NUMBER; } [0-9][0-9_]* { @@ -199,6 +199,7 @@ W [ \t\b\f\r]+ } yylval.number = new verinum(bits, nbits, false); + yylval.number->has_sign(true); delete[]bits; return NUMBER; } @@ -313,10 +314,16 @@ void lex_end_table() static verinum*make_binary_with_size(unsigned size, bool fixed, const char*ptr) { - assert(tolower(*ptr) == 'b'); + bool sign_flag = false; verinum::V*bits = new verinum::V[size]; + if (tolower(ptr[0]) == 's') { + ptr += 1; + sign_flag = true; + } + assert(tolower(*ptr) == 'b'); ptr += 1; + while (*ptr && ((*ptr == ' ') || (*ptr == '\t'))) ptr += 1; @@ -364,7 +371,10 @@ static verinum*make_binary_with_size(unsigned size, bool fixed, const char*ptr) } } - return new verinum(bits, size, fixed); + verinum*out = new verinum(bits, size, fixed); + delete[]bits; + out->has_sign(sign_flag); + return out; } static verinum*make_sized_binary(const char*txt) @@ -375,16 +385,21 @@ static verinum*make_sized_binary(const char*txt) ptr += 1; assert(*ptr == '\''); ptr += 1; - assert(tolower(*ptr) == 'b'); return make_binary_with_size(size, true, ptr); } static verinum*make_unsized_binary(const char*txt) { + bool sign_flag = false; const char*ptr = txt; assert(*ptr == '\''); ptr += 1; + + if (tolower(*ptr) == 's') { + sign_flag = true; + ptr += 1; + } assert(tolower(*ptr) == 'b'); while (*ptr && ((*ptr == 'b') || (*ptr == ' ') || (*ptr == '\t'))) ptr += 1; @@ -419,17 +434,27 @@ static verinum*make_unsized_binary(const char*txt) ptr += 1; } - return new verinum(bits, size); + verinum*out = new verinum(bits, size); + out->has_sign(sign_flag); + delete[]bits; + return out; } static verinum*make_sized_octal(const char*txt) { + bool sign_flag = false; char*ptr; + unsigned size = strtoul(txt,&ptr,10); while (*ptr && ((*ptr == ' ') || (*ptr == '\t'))) ptr += 1; assert(*ptr == '\''); ptr += 1; + + if (tolower(*ptr) == 's') { + sign_flag = true; + ptr += 1; + } assert(tolower(*ptr) == 'o'); /* We know from the size number how bit to make the verinom @@ -505,14 +530,24 @@ static verinum*make_sized_octal(const char*txt) } } - return new verinum(bits, size, true); + verinum*out = new verinum(bits, size, true); + delete[]bits; + out->has_sign(sign_flag); + return out; } static verinum*make_unsized_octal(const char*txt) { + bool sign_flag = false; const char*ptr = txt; assert(*ptr == '\''); ptr += 1; + + if (tolower(*ptr) == 's') { + sign_flag = true; + ptr += 1; + } + assert(tolower(*ptr) == 'o'); ptr += 1; @@ -554,11 +589,15 @@ static verinum*make_unsized_octal(const char*txt) ptr += 1; } - return new verinum(bits, size); + verinum*out = new verinum(bits, size); + out->has_sign(sign_flag); + delete[]bits; + return out; } static verinum*make_sized_hex(const char*txt) { + bool sign_flag = false; char*ptr; unsigned size = strtoul(txt,&ptr,10); @@ -567,6 +606,12 @@ static verinum*make_sized_hex(const char*txt) assert(*ptr == '\''); ptr += 1; + + if (tolower(*ptr) == 's') { + sign_flag = true; + ptr += 1; + } + assert(tolower(*ptr) == 'h'); ptr += 1; @@ -633,14 +678,23 @@ static verinum*make_sized_hex(const char*txt) bits[idx++] = verinum::V0; } - return new verinum(bits, size, true); + verinum*out = new verinum(bits, size, true); + out->has_sign(sign_flag); + delete[]bits; + return out; } static verinum*make_unsized_hex(const char*txt) { + bool sign_flag = false; const char*ptr = txt; assert(*ptr == '\''); ptr += 1; + + if (tolower(*ptr) == 's') { + sign_flag = true; + ptr += 1; + } assert(tolower(*ptr) == 'h'); ptr += 1; @@ -693,7 +747,10 @@ static verinum*make_unsized_hex(const char*txt) ptr += 1; } - return new verinum(bits, size); + verinum*out = new verinum(bits, size); + out->has_sign(sign_flag); + delete[]bits; + return out; } /* @@ -702,6 +759,11 @@ static verinum*make_unsized_hex(const char*txt) */ static verinum*make_dec_with_size(unsigned size, bool fixed, const char*ptr) { + bool signed_flag = false; + if (tolower(*ptr) == 's') { + signed_flag = true; + ptr += 1; + } assert(tolower(*ptr) == 'd'); ptr += 1; @@ -725,7 +787,10 @@ static verinum*make_dec_with_size(unsigned size, bool fixed, const char*ptr) value /= 2; } - return new verinum(bits, size, fixed); + verinum*out = new verinum(bits, size, fixed); + out->has_sign(signed_flag); + delete[]bits; + return out; } static verinum*make_sized_dec(const char*txt) @@ -738,7 +803,6 @@ static verinum*make_sized_dec(const char*txt) assert(*ptr == '\''); ptr += 1; - assert(tolower(*ptr) == 'd'); return make_dec_with_size(size, true, ptr); } diff --git a/verinum.cc b/verinum.cc index e94031ad4..0b93bc7c9 100644 --- a/verinum.cc +++ b/verinum.cc @@ -17,7 +17,7 @@ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA */ #if !defined(WINNT) -#ident "$Id: verinum.cc,v 1.13 2000/01/06 05:57:06 steve Exp $" +#ident "$Id: verinum.cc,v 1.14 2000/01/07 03:45:49 steve Exp $" #endif # include "verinum.h" @@ -25,12 +25,12 @@ # include verinum::verinum() -: bits_(0), nbits_(0), has_len_(false), string_flag_(false) +: bits_(0), nbits_(0), has_len_(false), has_sign_(false), string_flag_(false) { } verinum::verinum(const V*bits, unsigned nbits, bool has_len) -: has_len_(has_len), string_flag_(false) +: has_len_(has_len), has_sign_(false), string_flag_(false) { nbits_ = nbits; bits_ = new V [nbits]; @@ -40,7 +40,7 @@ verinum::verinum(const V*bits, unsigned nbits, bool has_len) } verinum::verinum(const string&str) -: has_len_(true), string_flag_(true) +: has_len_(true), has_sign_(false), string_flag_(true) { nbits_ = str.length() * 8; bits_ = new V [nbits_]; @@ -61,7 +61,7 @@ verinum::verinum(const string&str) } verinum::verinum(verinum::V val, unsigned n) -: has_len_(true), string_flag_(false) +: has_len_(true), has_sign_(false), string_flag_(false) { nbits_ = n; bits_ = new V[nbits_]; @@ -70,7 +70,7 @@ verinum::verinum(verinum::V val, unsigned n) } verinum::verinum(unsigned long val, unsigned n) -: has_len_(true), string_flag_(false) +: has_len_(true), has_sign_(false), string_flag_(false) { nbits_ = n; bits_ = new V[nbits_]; @@ -86,6 +86,7 @@ verinum::verinum(const verinum&that) nbits_ = that.nbits_; bits_ = new V[nbits_]; has_len_ = that.has_len_; + has_sign_ = that.has_sign_; for (unsigned idx = 0 ; idx < nbits_ ; idx += 1) bits_[idx] = that.bits_[idx]; } @@ -97,6 +98,7 @@ verinum::verinum(const verinum&that, unsigned nbits) nbits_ = nbits; bits_ = new V[nbits_]; has_len_ = true; + has_sign_ = false; for (unsigned idx = 0 ; idx < nbits_ ; idx += 1) bits_[idx] = that.bits_[idx]; } @@ -116,6 +118,7 @@ verinum& verinum::operator= (const verinum&that) bits_[idx] = that.bits_[idx]; has_len_ = that.has_len_; + has_sign_ = that.has_sign_; string_flag_ = that.string_flag_; return *this; } @@ -164,9 +167,9 @@ signed long verinum::as_long() const signed long val = 0; - // Extend the sign bit to fill the long. (but only for unsized + // Extend the sign bit to fill the long. (But only for signed // numbers.) - if ((has_len_ == false) && (bits_[nbits_-1] == V1)) + if (has_sign_ && (bits_[nbits_-1] == V1)) val = -1; for (unsigned idx = nbits_ ; idx > 0 ; idx -= 1) { @@ -468,6 +471,9 @@ verinum operator - (const verinum&left, const verinum&r) /* * $Log: verinum.cc,v $ + * Revision 1.14 2000/01/07 03:45:49 steve + * Initial support for signed constants. + * * Revision 1.13 2000/01/06 05:57:06 steve * Only sign-extend unsized numbers. * diff --git a/verinum.h b/verinum.h index b9a86a505..257e582f3 100644 --- a/verinum.h +++ b/verinum.h @@ -19,7 +19,7 @@ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA */ #if !defined(WINNT) -#ident "$Id: verinum.h,v 1.8 1999/11/06 16:00:17 steve Exp $" +#ident "$Id: verinum.h,v 1.9 2000/01/07 03:45:49 steve Exp $" #endif # include @@ -56,6 +56,9 @@ class verinum { // in some way. bool has_len() const { return has_len_; } + bool has_sign(bool flag) { has_sign_ = flag; return has_sign_; } + bool has_sign() const { return has_sign_; } + // A number is "defined" if there are no x or z bits in its value. bool is_defined() const; @@ -82,6 +85,7 @@ class verinum { V* bits_; unsigned nbits_; bool has_len_; + bool has_sign_; // These are some convenience flags that help us do a better // job of pretty-printing values. @@ -100,6 +104,9 @@ extern verinum operator - (const verinum&left, const verinum&right); /* * $Log: verinum.h,v $ + * Revision 1.9 2000/01/07 03:45:49 steve + * Initial support for signed constants. + * * Revision 1.8 1999/11/06 16:00:17 steve * Put number constants into a static table. *