2 * Integer number functions.
4 * Copyright (C) 2001-2007 Peter Johnson
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
9 * 1. Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * 2. Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND OTHER CONTRIBUTORS ``AS IS''
16 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR OTHER CONTRIBUTORS BE
19 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
20 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
21 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
22 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
23 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
24 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
25 * POSSIBILITY OF SUCH DAMAGE.
40 /* "Native" "word" size for intnum calculations. */
41 #define BITVECT_NATIVE_SIZE 256
45 long l; /* integer value (for integers <32 bits) */
46 wordptr bv; /* bit vector (for integers >=32 bits) */
48 enum { INTNUM_L, INTNUM_BV } type;
51 /* static bitvect used for conversions */
52 static /*@only@*/ wordptr conv_bv;
54 /* static bitvects used for computation */
55 static /*@only@*/ wordptr result, spare, op1static, op2static;
57 static /*@only@*/ BitVector_from_Dec_static_data *from_dec_data;
61 yasm_intnum_initialize(void)
63 conv_bv = BitVector_Create(BITVECT_NATIVE_SIZE, FALSE);
64 result = BitVector_Create(BITVECT_NATIVE_SIZE, FALSE);
65 spare = BitVector_Create(BITVECT_NATIVE_SIZE, FALSE);
66 op1static = BitVector_Create(BITVECT_NATIVE_SIZE, FALSE);
67 op2static = BitVector_Create(BITVECT_NATIVE_SIZE, FALSE);
68 from_dec_data = BitVector_from_Dec_static_Boot(BITVECT_NATIVE_SIZE);
72 yasm_intnum_cleanup(void)
74 BitVector_from_Dec_static_Shutdown(from_dec_data);
75 BitVector_Destroy(op2static);
76 BitVector_Destroy(op1static);
77 BitVector_Destroy(spare);
78 BitVector_Destroy(result);
79 BitVector_Destroy(conv_bv);
82 /* Compress a bitvector into intnum storage.
83 * If saved as a bitvector, clones the passed bitvector.
84 * Can modify the passed bitvector.
87 intnum_frombv(/*@out@*/ yasm_intnum *intn, wordptr bv)
89 if (Set_Max(bv) < 31) {
90 intn->type = INTNUM_L;
91 intn->val.l = (long)BitVector_Chunk_Read(bv, 31, 0);
92 } else if (BitVector_msb_(bv)) {
93 /* Negative, negate and see if we'll fit into a long. */
95 BitVector_Negate(bv, bv);
96 if (Set_Max(bv) >= 32 ||
97 ((ul = BitVector_Chunk_Read(bv, 32, 0)) & 0x80000000)) {
99 BitVector_Negate(bv, bv);
100 intn->type = INTNUM_BV;
101 intn->val.bv = BitVector_Clone(bv);
103 intn->type = INTNUM_L;
104 intn->val.l = -((long)ul);
107 intn->type = INTNUM_BV;
108 intn->val.bv = BitVector_Clone(bv);
112 /* If intnum is a BV, returns its bitvector directly.
113 * If not, converts into passed bv and returns that instead.
116 intnum_tobv(/*@returned@*/ wordptr bv, const yasm_intnum *intn)
118 if (intn->type == INTNUM_BV)
122 if (intn->val.l >= 0)
123 BitVector_Chunk_Store(bv, 32, 0, (unsigned long)intn->val.l);
125 BitVector_Chunk_Store(bv, 32, 0, (unsigned long)-intn->val.l);
126 BitVector_Negate(bv, bv);
132 yasm_intnum_create_dec(char *str)
134 yasm_intnum *intn = yasm_xmalloc(sizeof(yasm_intnum));
136 switch (BitVector_from_Dec_static(from_dec_data, conv_bv,
137 (unsigned char *)str)) {
139 yasm_error_set(YASM_ERROR_VALUE, N_("invalid decimal literal"));
142 yasm_error_set(YASM_ERROR_OVERFLOW,
143 N_("Numeric constant too large for internal format"));
148 intnum_frombv(intn, conv_bv);
153 yasm_intnum_create_bin(char *str)
155 yasm_intnum *intn = yasm_xmalloc(sizeof(yasm_intnum));
157 switch (BitVector_from_Bin(conv_bv, (unsigned char *)str)) {
159 yasm_error_set(YASM_ERROR_VALUE, N_("invalid binary literal"));
162 yasm_error_set(YASM_ERROR_OVERFLOW,
163 N_("Numeric constant too large for internal format"));
168 intnum_frombv(intn, conv_bv);
173 yasm_intnum_create_oct(char *str)
175 yasm_intnum *intn = yasm_xmalloc(sizeof(yasm_intnum));
177 switch (BitVector_from_Oct(conv_bv, (unsigned char *)str)) {
179 yasm_error_set(YASM_ERROR_VALUE, N_("invalid octal literal"));
182 yasm_error_set(YASM_ERROR_OVERFLOW,
183 N_("Numeric constant too large for internal format"));
188 intnum_frombv(intn, conv_bv);
193 yasm_intnum_create_hex(char *str)
195 yasm_intnum *intn = yasm_xmalloc(sizeof(yasm_intnum));
197 switch (BitVector_from_Hex(conv_bv, (unsigned char *)str)) {
199 yasm_error_set(YASM_ERROR_VALUE, N_("invalid hex literal"));
202 yasm_error_set(YASM_ERROR_OVERFLOW,
203 N_("Numeric constant too large for internal format"));
208 intnum_frombv(intn, conv_bv);
212 /*@-usedef -compdef -uniondef@*/
214 yasm_intnum_create_charconst_nasm(const char *str)
216 yasm_intnum *intn = yasm_xmalloc(sizeof(yasm_intnum));
217 size_t len = strlen(str);
219 if(len*8 > BITVECT_NATIVE_SIZE)
220 yasm_error_set(YASM_ERROR_OVERFLOW,
221 N_("Character constant too large for internal format"));
223 /* be conservative in choosing bitvect in case MSB is set */
225 BitVector_Empty(conv_bv);
226 intn->type = INTNUM_BV;
229 intn->type = INTNUM_L;
234 intn->val.l |= ((unsigned long)str[2]) & 0xff;
238 intn->val.l |= ((unsigned long)str[1]) & 0xff;
242 intn->val.l |= ((unsigned long)str[0]) & 0xff;
246 /* >=32 bit conversion */
248 BitVector_Move_Left(conv_bv, 8);
249 BitVector_Chunk_Store(conv_bv, 8, 0,
250 ((unsigned long)str[--len]) & 0xff);
252 intn->val.bv = BitVector_Clone(conv_bv);
259 yasm_intnum_create_charconst_tasm(const char *str)
261 yasm_intnum *intn = yasm_xmalloc(sizeof(yasm_intnum));
262 size_t len = strlen(str);
265 if(len*8 > BITVECT_NATIVE_SIZE)
266 yasm_error_set(YASM_ERROR_OVERFLOW,
267 N_("Character constant too large for internal format"));
269 /* be conservative in choosing bitvect in case MSB is set */
271 BitVector_Empty(conv_bv);
272 intn->type = INTNUM_BV;
275 intn->type = INTNUM_L;
278 /* tasm uses big endian notation */
282 intn->val.l |= ((unsigned long)str[i++]) & 0xff;
286 intn->val.l |= ((unsigned long)str[i++]) & 0xff;
290 intn->val.l |= ((unsigned long)str[i++]) & 0xff;
294 /* >=32 bit conversion */
296 BitVector_Chunk_Store(conv_bv, 8, (len-i-1)*8,
297 ((unsigned long)str[i]) & 0xff);
300 intn->val.bv = BitVector_Clone(conv_bv);
305 /*@=usedef =compdef =uniondef@*/
308 yasm_intnum_create_uint(unsigned long i)
310 yasm_intnum *intn = yasm_xmalloc(sizeof(yasm_intnum));
313 /* Too big, store as bitvector */
314 intn->val.bv = BitVector_Create(BITVECT_NATIVE_SIZE, TRUE);
315 intn->type = INTNUM_BV;
316 BitVector_Chunk_Store(intn->val.bv, 32, 0, i);
318 intn->val.l = (long)i;
319 intn->type = INTNUM_L;
326 yasm_intnum_create_int(long i)
328 yasm_intnum *intn = yasm_xmalloc(sizeof(yasm_intnum));
331 intn->type = INTNUM_L;
337 yasm_intnum_create_leb128(const unsigned char *ptr, int sign,
340 yasm_intnum *intn = yasm_xmalloc(sizeof(yasm_intnum));
341 const unsigned char *ptr_orig = ptr;
344 BitVector_Empty(conv_bv);
346 BitVector_Chunk_Store(conv_bv, 7, i, *ptr);
348 if ((*ptr & 0x80) != 0x80)
353 *size = (unsigned long)(ptr-ptr_orig)+1;
355 if(i > BITVECT_NATIVE_SIZE)
356 yasm_error_set(YASM_ERROR_OVERFLOW,
357 N_("Numeric constant too large for internal format"));
358 else if (sign && (*ptr & 0x40) == 0x40)
359 BitVector_Interval_Fill(conv_bv, i, BITVECT_NATIVE_SIZE-1);
361 intnum_frombv(intn, conv_bv);
366 yasm_intnum_create_sized(unsigned char *ptr, int sign, size_t srcsize,
369 yasm_intnum *intn = yasm_xmalloc(sizeof(yasm_intnum));
372 if (srcsize*8 > BITVECT_NATIVE_SIZE)
373 yasm_error_set(YASM_ERROR_OVERFLOW,
374 N_("Numeric constant too large for internal format"));
376 /* Read the buffer into a bitvect */
377 BitVector_Empty(conv_bv);
380 yasm_internal_error(N_("big endian not implemented"));
382 for (i = 0; i < srcsize; i++)
383 BitVector_Chunk_Store(conv_bv, 8, i*8, ptr[i]);
386 /* Sign extend if needed */
387 if (srcsize*8 < BITVECT_NATIVE_SIZE && sign && (ptr[i-1] & 0x80) == 0x80)
388 BitVector_Interval_Fill(conv_bv, i*8, BITVECT_NATIVE_SIZE-1);
390 intnum_frombv(intn, conv_bv);
395 yasm_intnum_copy(const yasm_intnum *intn)
397 yasm_intnum *n = yasm_xmalloc(sizeof(yasm_intnum));
399 switch (intn->type) {
401 n->val.l = intn->val.l;
404 n->val.bv = BitVector_Clone(intn->val.bv);
407 n->type = intn->type;
413 yasm_intnum_destroy(yasm_intnum *intn)
415 if (intn->type == INTNUM_BV)
416 BitVector_Destroy(intn->val.bv);
420 /*@-nullderef -nullpass -branchstate@*/
422 yasm_intnum_calc(yasm_intnum *acc, yasm_expr_op op, yasm_intnum *operand)
425 wordptr op1, op2 = NULL;
428 /* Always do computations with in full bit vector.
429 * Bit vector results must be calculated through intermediate storage.
431 op1 = intnum_tobv(op1static, acc);
433 op2 = intnum_tobv(op2static, operand);
435 if (!operand && op != YASM_EXPR_NEG && op != YASM_EXPR_NOT &&
436 op != YASM_EXPR_LNOT) {
437 yasm_error_set(YASM_ERROR_ARITHMETIC,
438 N_("operation needs an operand"));
439 BitVector_Empty(result);
443 /* A operation does a bitvector computation if result is allocated. */
446 BitVector_add(result, op1, op2, &carry);
449 BitVector_sub(result, op1, op2, &carry);
452 BitVector_Multiply(result, op1, op2);
455 /* TODO: make sure op1 and op2 are unsigned */
456 if (BitVector_is_empty(op2)) {
457 yasm_error_set(YASM_ERROR_ZERO_DIVISION, N_("divide by zero"));
458 BitVector_Empty(result);
461 BitVector_Divide(result, op1, op2, spare);
463 case YASM_EXPR_SIGNDIV:
464 if (BitVector_is_empty(op2)) {
465 yasm_error_set(YASM_ERROR_ZERO_DIVISION, N_("divide by zero"));
466 BitVector_Empty(result);
469 BitVector_Divide(result, op1, op2, spare);
472 /* TODO: make sure op1 and op2 are unsigned */
473 if (BitVector_is_empty(op2)) {
474 yasm_error_set(YASM_ERROR_ZERO_DIVISION, N_("divide by zero"));
475 BitVector_Empty(result);
478 BitVector_Divide(spare, op1, op2, result);
480 case YASM_EXPR_SIGNMOD:
481 if (BitVector_is_empty(op2)) {
482 yasm_error_set(YASM_ERROR_ZERO_DIVISION, N_("divide by zero"));
483 BitVector_Empty(result);
486 BitVector_Divide(spare, op1, op2, result);
489 BitVector_Negate(result, op1);
492 Set_Complement(result, op1);
495 Set_Union(result, op1, op2);
498 Set_Intersection(result, op1, op2);
501 Set_ExclusiveOr(result, op1, op2);
504 Set_ExclusiveOr(result, op1, op2);
505 Set_Complement(result, result);
508 Set_Union(result, op1, op2);
509 Set_Complement(result, result);
512 if (operand->type == INTNUM_L && operand->val.l >= 0) {
513 BitVector_Copy(result, op1);
514 BitVector_Move_Left(result, (N_int)operand->val.l);
515 } else /* don't even bother, just zero result */
516 BitVector_Empty(result);
519 if (operand->type == INTNUM_L && operand->val.l >= 0) {
520 BitVector_Copy(result, op1);
521 carry = BitVector_msb_(op1);
522 count = (N_int)operand->val.l;
524 BitVector_shift_right(result, carry);
525 } else /* don't even bother, just zero result */
526 BitVector_Empty(result);
529 BitVector_Empty(result);
530 BitVector_LSB(result, !BitVector_is_empty(op1) ||
531 !BitVector_is_empty(op2));
534 BitVector_Empty(result);
535 BitVector_LSB(result, !BitVector_is_empty(op1) &&
536 !BitVector_is_empty(op2));
539 BitVector_Empty(result);
540 BitVector_LSB(result, BitVector_is_empty(op1));
543 BitVector_Empty(result);
544 BitVector_LSB(result, !BitVector_is_empty(op1) ^
545 !BitVector_is_empty(op2));
547 case YASM_EXPR_LXNOR:
548 BitVector_Empty(result);
549 BitVector_LSB(result, !(!BitVector_is_empty(op1) ^
550 !BitVector_is_empty(op2)));
553 BitVector_Empty(result);
554 BitVector_LSB(result, !(!BitVector_is_empty(op1) ||
555 !BitVector_is_empty(op2)));
558 BitVector_Empty(result);
559 BitVector_LSB(result, BitVector_equal(op1, op2));
562 BitVector_Empty(result);
563 BitVector_LSB(result, BitVector_Compare(op1, op2) < 0);
566 BitVector_Empty(result);
567 BitVector_LSB(result, BitVector_Compare(op1, op2) > 0);
570 BitVector_Empty(result);
571 BitVector_LSB(result, BitVector_Compare(op1, op2) <= 0);
574 BitVector_Empty(result);
575 BitVector_LSB(result, BitVector_Compare(op1, op2) >= 0);
578 BitVector_Empty(result);
579 BitVector_LSB(result, !BitVector_equal(op1, op2));
582 yasm_error_set(YASM_ERROR_ARITHMETIC, N_("invalid use of '%s'"),
586 yasm_error_set(YASM_ERROR_ARITHMETIC, N_("invalid use of '%s'"),
589 case YASM_EXPR_SEGOFF:
590 yasm_error_set(YASM_ERROR_ARITHMETIC, N_("invalid use of '%s'"),
593 case YASM_EXPR_IDENT:
595 BitVector_Copy(result, op1);
598 yasm_error_set(YASM_ERROR_ARITHMETIC,
599 N_("invalid operation in intnum calculation"));
600 BitVector_Empty(result);
604 /* Try to fit the result into 32 bits if possible */
605 if (acc->type == INTNUM_BV)
606 BitVector_Destroy(acc->val.bv);
607 intnum_frombv(acc, result);
610 /*@=nullderef =nullpass =branchstate@*/
613 yasm_intnum_compare(const yasm_intnum *intn1, const yasm_intnum *intn2)
617 if (intn1->type == INTNUM_L && intn2->type == INTNUM_L) {
618 if (intn1->val.l < intn2->val.l)
620 if (intn1->val.l > intn2->val.l)
625 op1 = intnum_tobv(op1static, intn1);
626 op2 = intnum_tobv(op2static, intn2);
627 return BitVector_Compare(op1, op2);
631 yasm_intnum_zero(yasm_intnum *intn)
633 yasm_intnum_set_int(intn, 0);
637 yasm_intnum_set(yasm_intnum *intn, const yasm_intnum *val)
639 if (intn->type == val->type) {
642 intn->val.l = val->val.l;
645 BitVector_Copy(intn->val.bv, val->val.bv);
651 BitVector_Destroy(intn->val.bv);
652 intn->val.l = val->val.l;
655 intn->val.bv = BitVector_Clone(val->val.bv);
658 intn->type = val->type;
663 yasm_intnum_set_uint(yasm_intnum *intn, unsigned long val)
665 if (val > LONG_MAX) {
666 if (intn->type != INTNUM_BV) {
667 intn->val.bv = BitVector_Create(BITVECT_NATIVE_SIZE, TRUE);
668 intn->type = INTNUM_BV;
670 BitVector_Chunk_Store(intn->val.bv, 32, 0, val);
672 if (intn->type == INTNUM_BV) {
673 BitVector_Destroy(intn->val.bv);
674 intn->type = INTNUM_L;
676 intn->val.l = (long)val;
681 yasm_intnum_set_int(yasm_intnum *intn, long val)
683 if (intn->type == INTNUM_BV)
684 BitVector_Destroy(intn->val.bv);
685 intn->type = INTNUM_L;
690 yasm_intnum_is_zero(const yasm_intnum *intn)
692 return (intn->type == INTNUM_L && intn->val.l == 0);
696 yasm_intnum_is_pos1(const yasm_intnum *intn)
698 return (intn->type == INTNUM_L && intn->val.l == 1);
702 yasm_intnum_is_neg1(const yasm_intnum *intn)
704 return (intn->type == INTNUM_L && intn->val.l == -1);
708 yasm_intnum_sign(const yasm_intnum *intn)
710 if (intn->type == INTNUM_L) {
711 if (intn->val.l == 0)
713 else if (intn->val.l < 0)
718 return BitVector_Sign(intn->val.bv);
722 yasm_intnum_get_uint(const yasm_intnum *intn)
724 switch (intn->type) {
728 return (unsigned long)intn->val.l;
730 if (BitVector_msb_(intn->val.bv))
732 if (Set_Max(intn->val.bv) > 32)
734 return BitVector_Chunk_Read(intn->val.bv, 32, 0);
736 yasm_internal_error(N_("unknown intnum type"));
743 yasm_intnum_get_int(const yasm_intnum *intn)
745 switch (intn->type) {
749 if (BitVector_msb_(intn->val.bv)) {
750 /* it's negative: negate the bitvector to get a positive
751 * number, then negate the positive number.
755 BitVector_Negate(conv_bv, intn->val.bv);
756 if (Set_Max(conv_bv) >= 32) {
760 ul = BitVector_Chunk_Read(conv_bv, 32, 0);
761 /* check for too negative */
762 return (ul & 0x80000000) ? LONG_MIN : -((long)ul);
765 /* it's positive, and since it's a BV, it must be >0x7FFFFFFF */
768 yasm_internal_error(N_("unknown intnum type"));
775 yasm_intnum_get_sized(const yasm_intnum *intn, unsigned char *ptr,
776 size_t destsize, size_t valsize, int shift,
777 int bigendian, int warn)
779 wordptr op1 = op1static, op2;
782 size_t rshift = shift < 0 ? (size_t)(-shift) : 0;
785 /* Currently don't support destinations larger than our native size */
786 if (destsize*8 > BITVECT_NATIVE_SIZE)
787 yasm_internal_error(N_("destination too large"));
789 /* General size warnings */
790 if (warn<0 && !yasm_intnum_check_size(intn, valsize, rshift, 1))
791 yasm_warn_set(YASM_WARN_GENERAL,
792 N_("value does not fit in signed %d bit field"),
794 if (warn>0 && !yasm_intnum_check_size(intn, valsize, rshift, 2))
795 yasm_warn_set(YASM_WARN_GENERAL,
796 N_("value does not fit in %d bit field"), valsize);
798 /* Read the original data into a bitvect */
801 yasm_internal_error(N_("big endian not implemented"));
803 BitVector_Block_Store(op1, ptr, (N_int)destsize);
805 /* If not already a bitvect, convert value to be written to a bitvect */
806 op2 = intnum_tobv(op2static, intn);
808 /* Check low bits if right shifting and warnings enabled */
809 if (warn && rshift > 0) {
810 BitVector_Copy(conv_bv, op2);
811 BitVector_Move_Left(conv_bv, (N_int)(BITVECT_NATIVE_SIZE-rshift));
812 if (!BitVector_is_empty(conv_bv))
813 yasm_warn_set(YASM_WARN_GENERAL,
814 N_("misaligned value, truncating to boundary"));
817 /* Shift right if needed */
819 carry_in = BitVector_msb_(op2);
821 BitVector_shift_right(op2, carry_in);
825 /* Write the new value into the destination bitvect */
826 BitVector_Interval_Copy(op1, op2, (unsigned int)shift, 0, (N_int)valsize);
828 /* Write out the new data */
829 buf = BitVector_Block_Read(op1, &len);
832 yasm_internal_error(N_("big endian not implemented"));
834 memcpy(ptr, buf, destsize);
838 /* Return 1 if okay size, 0 if not */
840 yasm_intnum_check_size(const yasm_intnum *intn, size_t size, size_t rshift,
845 /* If not already a bitvect, convert value to a bitvect */
846 if (intn->type == INTNUM_BV) {
849 BitVector_Copy(val, intn->val.bv);
853 val = intnum_tobv(conv_bv, intn);
855 if (size >= BITVECT_NATIVE_SIZE)
859 int carry_in = BitVector_msb_(val);
861 BitVector_shift_right(val, carry_in);
865 if (BitVector_msb_(val)) {
869 BitVector_Negate(conv_bv, val);
870 BitVector_dec(conv_bv, conv_bv);
871 retval = Set_Max(conv_bv) < (long)size-1;
879 return (Set_Max(val) < (long)size);
883 yasm_intnum_in_range(const yasm_intnum *intn, long low, long high)
885 wordptr val = intnum_tobv(result, intn);
886 wordptr lval = op1static;
887 wordptr hval = op2static;
889 /* Convert high and low to bitvects */
890 BitVector_Empty(lval);
892 BitVector_Chunk_Store(lval, 32, 0, (unsigned long)low);
894 BitVector_Chunk_Store(lval, 32, 0, (unsigned long)(-low));
895 BitVector_Negate(lval, lval);
898 BitVector_Empty(hval);
900 BitVector_Chunk_Store(hval, 32, 0, (unsigned long)high);
902 BitVector_Chunk_Store(hval, 32, 0, (unsigned long)(-high));
903 BitVector_Negate(hval, hval);
907 return (BitVector_Compare(val, lval) >= 0
908 && BitVector_Compare(val, hval) <= 0);
912 get_leb128(wordptr val, unsigned char *ptr, int sign)
914 unsigned long i, size;
915 unsigned char *ptr_orig = ptr;
919 if (BitVector_msb_(val)) {
921 BitVector_Negate(conv_bv, val);
922 size = Set_Max(conv_bv)+2;
925 size = Set_Max(val)+2;
929 size = Set_Max(val)+1;
932 /* Positive/Unsigned write */
933 for (i=0; i<size; i += 7) {
934 *ptr = (unsigned char)BitVector_Chunk_Read(val, 7, i);
938 *(ptr-1) &= 0x7F; /* Clear MSB of last byte */
939 return (unsigned long)(ptr-ptr_orig);
943 size_leb128(wordptr val, int sign)
947 if (BitVector_msb_(val)) {
949 BitVector_Negate(conv_bv, val);
950 return (Set_Max(conv_bv)+8)/7;
953 return (Set_Max(val)+8)/7;
957 return (Set_Max(val)+7)/7;
962 yasm_intnum_get_leb128(const yasm_intnum *intn, unsigned char *ptr, int sign)
967 if (intn->type == INTNUM_L && intn->val.l == 0) {
972 /* If not already a bitvect, convert value to be written to a bitvect */
973 val = intnum_tobv(op1static, intn);
975 return get_leb128(val, ptr, sign);
979 yasm_intnum_size_leb128(const yasm_intnum *intn, int sign)
984 if (intn->type == INTNUM_L && intn->val.l == 0) {
988 /* If not already a bitvect, convert value to a bitvect */
989 val = intnum_tobv(op1static, intn);
991 return size_leb128(val, sign);
995 yasm_get_sleb128(long v, unsigned char *ptr)
997 wordptr val = op1static;
1005 BitVector_Empty(val);
1007 BitVector_Chunk_Store(val, 32, 0, (unsigned long)v);
1009 BitVector_Chunk_Store(val, 32, 0, (unsigned long)(-v));
1010 BitVector_Negate(val, val);
1012 return get_leb128(val, ptr, 1);
1016 yasm_size_sleb128(long v)
1018 wordptr val = op1static;
1023 BitVector_Empty(val);
1025 BitVector_Chunk_Store(val, 32, 0, (unsigned long)v);
1027 BitVector_Chunk_Store(val, 32, 0, (unsigned long)(-v));
1028 BitVector_Negate(val, val);
1030 return size_leb128(val, 1);
1034 yasm_get_uleb128(unsigned long v, unsigned char *ptr)
1036 wordptr val = op1static;
1044 BitVector_Empty(val);
1045 BitVector_Chunk_Store(val, 32, 0, v);
1046 return get_leb128(val, ptr, 0);
1050 yasm_size_uleb128(unsigned long v)
1052 wordptr val = op1static;
1057 BitVector_Empty(val);
1058 BitVector_Chunk_Store(val, 32, 0, v);
1059 return size_leb128(val, 0);
1063 yasm_intnum_get_str(const yasm_intnum *intn)
1067 switch (intn->type) {
1069 s = yasm_xmalloc(16);
1070 sprintf((char *)s, "%ld", intn->val.l);
1074 return (char *)BitVector_to_Dec(intn->val.bv);
1082 yasm_intnum_print(const yasm_intnum *intn, FILE *f)
1086 switch (intn->type) {
1088 fprintf(f, "0x%lx", intn->val.l);
1091 s = BitVector_to_Hex(intn->val.bv);
1092 fprintf(f, "0x%s", (char *)s);