Professional Documents
Culture Documents
CHP 2 Numbers
CHP 2 Numbers
In Detail
The bits of 8 bit binary numbers are numbered 0 to 7, with 0 being the least
significant digit, and 7 being the most significant.
The indices are labeled 0,1,2 etc above the binary digits, right to left. Then each
digit denotes the value digit * 2^index
741
= 512 + 229
= 512 + 128 + 101
= 512 + 128 + 64 + 37
= 512 + 128 + 64 + 32 + 5
= 512 + 128 + 64 + 32 + 4 + 1
(step)
A binary constant can be represented in the yasm assembler by appending b to a
string of 0s and 1s.
An alternative method is to keep dividing by 2. the reminder gives the binary digit
so
number /2 reminder binary number so far
741 370 1 1
370 185 0 01
185 92 1 101
92 46 0 0101
46 23 0 00101
23 11 1 100101
11 5 1 1100101
5 2 1 11100101
2 1 0 011100101
1 0 1 1011100101 = 741
The second method ==> you don't have to guess the closest power of 2, also easier
to program.
When the string is long, hexadecimal is more convenient than binary. As is decimal,
but it doesn't show us the pattern of 0s and 1s in the binary rperesentation
A hexadecimal number has base 16. It has digits 0--9 and then A,B,C,D,E,F.
Both yasm and C/C++ represent hexadecimal numbers with the prefix 0x.
Hex To Integer
Conversion to convert decimal to binary follows the same pattern as with binary
2586 = _ * 16^2 + _
= 10 * 256 + 26
= 10 * 256 + 1 * 16 + 10
= 10 * 16^2 + 1 * 16^1 + 10 * 16^0
= A 1 A
= 0xA1A
similarly
number /16 reminder hex so far
2586 161 10 = A A
161 10 1 1A
10 0 10 = A A1A = 0xA1A
Converting between binary and decimal and binary and hexadecimal is painful. But
(KEY) why do this? Use whatever format is convenient. If you want to use 1027 in a
decimal context, use decimal. If you want a (Binary) pattern you can chose binary
(short strings) or hexadecimal (long binary string).
2.3 Integers
unsigned 8 1 0 255
signed 8 1 -128 127
unsigned 16 2 0 65535
signed 16 2 -32768 32767
unsigned 32 4 0 4294967295
signed 32 4 -2147483648 2147483647
unsigned 64 8 0 large
number
signed 64 8 - large number large
number
The range of 64 bit integers is large enough for most needs (20! is larger!).
(KEY) Unsigned integers are precisely the binary numbers we saw earlier.
(KEY) (step) Signed integers are stored in a useful format called 2's complement.
(step)
The first bit of a signed integer is a sign bit - 0 ==> integer is positive. 1 ==>
number is negative.
attempt 1
The most obvious way to store the negative number would be to store the absolute
value of the number after the sign bit.
(_ KEY verification step: what we need is for the positive and negative numbers
with the same magnitude to add to zero. This fails with the scheme above as can be
seen from )
Corresponding negative number is 1 in the sign bit (For negative numbers) + bit
*complements* for the other bits in the positive numbers
But does this -1 representation work (_ for other numbers). What is 4 + -1?
4 0000 0100
-1 1111 1110 (from above)
gives 0000 0010 = 2 (instead of 3 the correct answer)
(step) Scheme 3:
Try 1 + -1
0000 0001
1111 1111
10000 0000 . the leftmost 1 is in the 9th position, which is thrown away to
get
Try 4 + -1
0000 0100
1111 1111
10000 0011 = throw away the leftmost 1 , 0000 0011. which is 3.
so this works
so for each multiple of 2 they have all ones till (and including) the position
which would indicate the number in the positive equivalent.
the largest possible negative number is 1000 0000. What is the magnitude of
this number?
(_ The largest negative number in 2's complement is the the negative equivalent of
the positive number represented by (unsigned binary number with) leftmost 1 and
rest 0s. see Patt for the reasoning)
(step)
Convert 2's complement binary to signed decimal
start with 1111 1101 0001 0010 == the number given is negative so we need to
calculate the magnitutde
=== (+ 1 complement (positive binary)))
=== 1111 1101 0001 0001 == (complement (positive binary))
=== 0000 0010 1110 1110 == positive binary
=== convert to integer === 750
(step)
convert hexadecimal to signed binary.
start with 0xFA13
so 0xFA13 = -1517
is like decimal multiplication. multiply one bit at a time and stagger to the left
1010101 *
10101
-------
1010101
1010101 <-- staggered two places because 2nd digit from right is 0
1010101
----------
11011111001
-----------
_none of these numbers are decrypted_
the IEEE format deals with all these numbers in the same way (?) but with different
lengths for fields.
in each format the highest order bit is the sign bit.
A negative number has the sign bit set to 1 and (KEY) all the other digits are just
like the corresponding positive number.
Each number has a binary exponent and a fraction.
The exponent (??) for a float is an 8 bit field. To allow for large numbers or
small numbers (_ which need negative exponents) the exponent is interpreted as
positive and negative. The actual value of the exponent is the value of the 8 bit
field minus 127. (_ this) 127 is the "exponent bias" for 32 bit floating point
numbers.
All other numbers have at least 1 bit, so the IEEE 754 format uses an implicit
1 bit to save space. (_ iow) if the fraction field is < 23 zeroes> it is
interpreted as 1. < 23 bits > . which allows the fraction field to be effectively
24 bits (??). This is made possible by making exponent fields 0x00 and 0xFF
special.
A number with exponent field == 0x00 is defined by 0. An exponent field value
of 0xFF is used to mean either positive or negative infinity. Many more details
exist for IEEE 754,but this is sufficient for our needs.
segment .data
zero dd 0.0
one dd 1.0
neg dd -1.0
a dd 1.75
b dd 122.5
d dd 1.1
e dd 10000000000.0
(_ work through
3F80 which is 0011 1111 1000 0000 .
so yes the sign bit = left most bit is 0.
exponent field = other 7 bits of the most significant byte + 1 bit from
the next byte = 0111 1111 which is 127 the exponent field value. and the actual
binary exponent is 0 (since it is exponent field value - 127, the "exponential
bias"). The remaining bits are the binary fraction field, all zeros.
The remaining bits are the binary fraction field - all 0s. Thus the value is 1.0 *
2^0 = 1.0
negative 1 (_ is BF80 which is 1011 1111 1000 0000 and so) the sign bit is 1,
the exponent field is 0111 1111 the same as above so the number is -1 * 1.0 * 2^0 )
(step)
you will notice that 1.75 and 122.5 have a significant number of 0s in the fraction
field.
(_ 1.75 is 3FE0 .. which is 0011 1111 1110 0000 0000 0000 0000 0000 ) this is
because 0.75 and .5 are both expressible as sums of negative powers of 2)
4097 decimal is 0x 00 00 10 01 but the cpu stores the least significant byte
first .
00 00 00 10 * 01 10 00 00 * b dd 4097