# Reading a signed byte in network byte order

**URL:** <https://rubytalk.org/t/reading-a-signed-byte-in-network-byte-order/22464>\
**Category:** ruby-talk\
**Created:** [14 November 2005 23:07 UTC](https://rubytalk.org/t/reading-a-signed-byte-in-network-byte-order/22464 "2005-11-14T23:07:01Z")\
**Posts on this page:** 8\
**Page:** 1

<div class="post-metadata">

**Author:** ![Robert\_Evans](https://avatars.discourse-cdn.com/v4/letter/r/9fc29f/32.png) [@Robert\_Evans](https://rubytalk.org/u/Robert_Evans)\
**Post date:** [14 November 2005 23:07 UTC](https://rubytalk.org/t/reading-a-signed-byte-in-network-byte-order/22464/1 "2005-11-14T23:07:01Z")

</div>

Hi,

In trying to read 4 bytes as a signed integer from an IO in big-endian order, is there already a utility to do this in Ruby? I notice unpack has lots of combinations already, but seemingly not one for this. Maybe I am just missing it?

Thanks,  
Bob Evans

---

<div class="post-metadata">

**Author:** ![Robert\_Evans](https://avatars.discourse-cdn.com/v4/letter/r/9fc29f/32.png) [@Robert\_Evans](https://rubytalk.org/u/Robert_Evans)\
**Post date:** [15 November 2005 16:13 UTC](https://rubytalk.org/t/reading-a-signed-byte-in-network-byte-order/22464/2 "2005-11-15T16:13:34Z")

</div>

Hi,

So, I came up with a solution, and would be grateful for Ruby style tips. It seemed a lot harder to do than it needed to be.

Any help appreciated.

Thanks,  
Bob

The Tests:

class ByteReaderTest \< Test::Unit::TestCase

&nbsp;&nbsp;&nbsp;def test\_read\_signed4\_negative  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;negative = "" \<\< 0xF2 \<\< 0x34 \<\< 0x56 \<\< 0x78  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;assert\_equal -231451016, signed4(StringIO.new(negative))  
&nbsp;&nbsp;&nbsp;end

&nbsp;&nbsp;&nbsp;def test\_read\_signed4\_positive  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;positive = "" \<\< 0x02 \<\< 0x34 \<\< 0x56 \<\< 0x78  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;assert\_equal 36984440, signed4(StringIO.new(positive))  
&nbsp;&nbsp;&nbsp;end

end

The Solution:

def signed4(file)  
&nbsp;&nbsp;&nbsp;bits = (file.read(4).unpack('B32'))[0]  
&nbsp;&nbsp;&nbsp;if bits[0..0].eql? "0" # sign bit is positive  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;bits.to\_i(2)  
&nbsp;&nbsp;&nbsp;else # sign bit is negative  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;compute\_negative\_number\_from(bits)  
&nbsp;&nbsp;&nbsp;end  
end

def compute\_negative\_number\_from(bits)  
&nbsp;&nbsp;&nbsp;twos\_complement = flip(bits).join.to\_i(2) + 1  
&nbsp;&nbsp;&nbsp;-1 \* twos\_complement  
end

def flip(bits)  
&nbsp;&nbsp;&nbsp;bits.scan(/\w/).collect { |bit| (bit.eql?("1")) ? "0" : "1" }  
end

> **···**
>
> On Nov 14, 2005, at 3:07 PM, Robert Evans wrote:
> 
> > Hi,
> > 
> > In trying to read 4 bytes as a signed integer from an IO in big-endian order, is there already a utility to do this in Ruby? I notice unpack has lots of combinations already, but seemingly not one for this. Maybe I am just missing it?
> > 
> > Thanks,  
> > Bob Evans

---

<div class="post-metadata">

**Author:** ![Joel\_VanderWerf1](https://avatars.discourse-cdn.com/v4/letter/j/94ad74/32.png) [@Joel\_VanderWerf1](https://rubytalk.org/u/Joel_VanderWerf1)\
**Post date:** [15 November 2005 23:10 UTC](https://rubytalk.org/t/reading-a-signed-byte-in-network-byte-order/22464/3 "2005-11-15T23:10:19Z")

</div>

Robert Evans wrote:

> Hi,
> 
> In trying to read 4 bytes as a signed integer from an IO in big- endian  
> order, is there already a utility to do this in Ruby? I notice unpack  
> has lots of combinations already, but seemingly not one for this. Maybe  
> I am just missing it?
> 
> Thanks,  
> Bob Evans

You can unpack with "N" and then use the following to interpret that  
positive Integer as a signed number in 32 bit two's complement  
representation and convert it to a positive or negative Integer:

&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;length = 32 # bits  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;max = 2\*\*length-1  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;mid = 2\*\*(length-1)  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;to\_signed = proc {|n| (n\>=mid) ? -((n ^ max) + 1) : n}

For example:

irb(main):012:0\> to\_signed[4294967295]  
=\> -1

This is a snippet from the implementation of my bit-struct lib (see  
RAA). A BitStruct is basically a string with some extra accessors and  
convenience methods. Currently it handles fields that are either  
multiple bytes or 1-7 bits within a byte. (Eventually, longer odd-size  
bit fields would be nice.) Also supports fields for: fixed length char  
strings, null-terminated strings, hex octets, decimal octets, floats,  
nested BitStructs, and "rest"--the rest of the string after defined  
fields. It's \*really\* useful for playing with net protocols in pure  
ruby. (Someday, I'll probably write a C extension for efficiency.)

Example:

require 'bit-struct'

class C \< BitStruct  
&nbsp;&nbsp;signed :foo, 32, "Something signed"  
&nbsp;&nbsp;unsigned :bar, 32, "Something UNsigned"  
end

c = C.new

c.foo = -12345678  
c.bar = 12345678

puts "-"\*40  
p c

puts "-"\*40  
p c.to\_s

puts "-"\*40  
puts c.inspect\_detailed

puts "-"\*40  
p c.to\_h

puts "-"\*40  
puts C.describe

\_\_END\_\_

> **···**
>
> ----------------------------------------  
> #\<C foo=-12345678, bar=12345678\>  
> ----------------------------------------  
> "\377C\236\262\000\274aN"  
> ----------------------------------------  
> C:  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Something signed = -12345678  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Something UNsigned = 12345678  
> ----------------------------------------  
> {:bar=\>12345678, :foo=\>-12345678}  
> ----------------------------------------  
> &nbsp;&nbsp;&nbsp;&nbsp;byte: type name [size] description  
> ----------------------------------------------------------------------  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;@0: signed foo [32b] Something signed  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;@4: unsigned bar [32b] Something UNsigned
> 
> --  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;vjoel : Joel VanderWerf : path berkeley edu : 510 665 3407

---

<div class="post-metadata">

**Author:** ![David\_Balmain1](https://avatars.discourse-cdn.com/v4/letter/d/76d3ee/32.png) [@David\_Balmain1](https://rubytalk.org/u/David_Balmain1)\
**Post date:** [15 November 2005 17:40 UTC](https://rubytalk.org/t/reading-a-signed-byte-in-network-byte-order/22464/4 "2005-11-15T17:40:24Z")

</div>

Hi Robert,

I'm probably missing something here, but how about this? It works for  
your tests at least.

def signed4(file)  
&nbsp;&nbsp;file.read(4).reverse.unpack('l')[0]  
end

Cheers,  
Dave

> **···**
>
> On 11/16/05, Robert Evans \<robert.evans@acm.org\> wrote:
> 
> > Hi,
> > 
> > So, I came up with a solution, and would be grateful for Ruby style  
> > tips. It seemed a lot harder to do than it needed to be.
> > 
> > Any help appreciated.
> > 
> > Thanks,  
> > Bob
> > 
> > The Tests:
> > 
> > class ByteReaderTest \< Test::Unit::TestCase
> > 
> > &nbsp;&nbsp;&nbsp;def test\_read\_signed4\_negative  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;negative = "" \<\< 0xF2 \<\< 0x34 \<\< 0x56 \<\< 0x78  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;assert\_equal -231451016, signed4(StringIO.new(negative))  
> > &nbsp;&nbsp;&nbsp;end
> > 
> > &nbsp;&nbsp;&nbsp;def test\_read\_signed4\_positive  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;positive = "" \<\< 0x02 \<\< 0x34 \<\< 0x56 \<\< 0x78  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;assert\_equal 36984440, signed4(StringIO.new(positive))  
> > &nbsp;&nbsp;&nbsp;end
> > 
> > end
> > 
> > The Solution:
> > 
> > def signed4(file)  
> > &nbsp;&nbsp;&nbsp;bits = (file.read(4).unpack('B32'))[0]  
> > &nbsp;&nbsp;&nbsp;if bits[0..0].eql? "0" # sign bit is positive  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;bits.to\_i(2)  
> > &nbsp;&nbsp;&nbsp;else # sign bit is negative  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;compute\_negative\_number\_from(bits)  
> > &nbsp;&nbsp;&nbsp;end  
> > end
> > 
> > def compute\_negative\_number\_from(bits)  
> > &nbsp;&nbsp;&nbsp;twos\_complement = flip(bits).join.to\_i(2) + 1  
> > &nbsp;&nbsp;&nbsp;-1 \* twos\_complement  
> > end
> > 
> > def flip(bits)  
> > &nbsp;&nbsp;&nbsp;bits.scan(/\w/).collect { |bit| (bit.eql?("1")) ? "0" : "1" }  
> > end
> > 
> > On Nov 14, 2005, at 3:07 PM, Robert Evans wrote:
> > 
> > \> Hi,  
> > \>  
> > \> In trying to read 4 bytes as a signed integer from an IO in big-  
> > \> endian order, is there already a utility to do this in Ruby? I  
> > \> notice unpack has lots of combinations already, but seemingly not  
> > \> one for this. Maybe I am just missing it?  
> > \>  
> > \> Thanks,  
> > \> Bob Evans  
> > \>

---

<div class="post-metadata">

**Author:** ![Ara.T.Howard6](https://avatars.discourse-cdn.com/v4/letter/a/958977/32.png) [@Ara.T.Howard6](https://rubytalk.org/u/Ara.T.Howard6)\
**Post date:** [15 November 2005 17:56 UTC](https://rubytalk.org/t/reading-a-signed-byte-in-network-byte-order/22464/5 "2005-11-15T17:56:09Z")

</div>

harp:~ \> cat a.rb  
require "test/unit"  
class ByteReaderTest \< Test::Unit::TestCase  
&nbsp;&nbsp;&nbsp;MAX\_POS = 2 \*\* 31 -1  
&nbsp;&nbsp;&nbsp;BIG\_ENDIAN = [42].pack('N') == [42].pack('i')  
&nbsp;&nbsp;&nbsp;def test\_read\_signed4\_positive  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;positive = [0x02, 0x34, 0x56, 0x78].pack "c\*"  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;assert\_equal 36984440, signed4(positive)  
&nbsp;&nbsp;&nbsp;end  
&nbsp;&nbsp;&nbsp;def test\_read\_signed4\_negative  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;negative = [0xF2, 0x34, 0x56, 0x78].pack "c\*"  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;assert\_equal -231451016, signed4(negative)  
&nbsp;&nbsp;&nbsp;end  
&nbsp;&nbsp;&nbsp;def signed4 buf  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;buf = buf.read 4 if buf.respond\_to? "read"  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;raise RangeError unless buf.size == 4  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;n = buf.unpack('N').first  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if n \> MAX\_POS  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(BIG\_ENDIAN ? buf : buf.reverse).unpack('l').first  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;n  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;end  
&nbsp;&nbsp;&nbsp;end  
end

harp:~ \> ruby a.rb  
Loaded suite a  
Started  
..  
Finished in 0.000583 seconds.

2 tests, 2 assertions, 0 failures, 0 errors

-a

> **···**
>
> On Wed, 16 Nov 2005, Robert Evans wrote:
> 
> > Hi,
> > 
> > So, I came up with a solution, and would be grateful for Ruby style tips. It seemed a lot harder to do than it needed to be.
> > 
> > Any help appreciated.
> > 
> > Thanks,  
> > Bob
> > 
> > The Tests:
> > 
> > class ByteReaderTest \< Test::Unit::TestCase
> > 
> > def test\_read\_signed4\_negative  
> > &nbsp;&nbsp;&nbsp;negative = "" \<\< 0xF2 \<\< 0x34 \<\< 0x56 \<\< 0x78  
> > &nbsp;&nbsp;&nbsp;assert\_equal -231451016, signed4(StringIO.new(negative))  
> > end
> > 
> > def test\_read\_signed4\_positive  
> > &nbsp;&nbsp;&nbsp;positive = "" \<\< 0x02 \<\< 0x34 \<\< 0x56 \<\< 0x78  
> > &nbsp;&nbsp;&nbsp;assert\_equal 36984440, signed4(StringIO.new(positive))  
> > end
> > 
> > end
> > 
> > The Solution:
> > 
> > def signed4(file)  
> > bits = (file.read(4).unpack('B32'))[0]  
> > if bits[0..0].eql? "0" # sign bit is positive  
> > &nbsp;&nbsp;&nbsp;bits.to\_i(2)  
> > else # sign bit is negative  
> > &nbsp;&nbsp;&nbsp;compute\_negative\_number\_from(bits)  
> > end  
> > end
> > 
> > def compute\_negative\_number\_from(bits)  
> > twos\_complement = flip(bits).join.to\_i(2) + 1  
> > -1 \* twos\_complement  
> > end
> > 
> > def flip(bits)  
> > bits.scan(/\w/).collect { |bit| (bit.eql?("1")) ? "0" : "1" }  
> > end
> 
> # --
> 
> > ara [dot] t [dot] howard [at] gmail [dot] com  
> > all happiness comes from the desire for others to be happy. all misery  
> > comes from the desire for oneself to be happy.  
> > -- bodhicaryavatara
> 
> ===============================================================================

---

<div class="post-metadata">

**Author:** ![Joel\_VanderWerf1](https://avatars.discourse-cdn.com/v4/letter/j/94ad74/32.png) [@Joel\_VanderWerf1](https://rubytalk.org/u/Joel_VanderWerf1)\
**Post date:** [15 November 2005 23:14 UTC](https://rubytalk.org/t/reading-a-signed-byte-in-network-byte-order/22464/6 "2005-11-15T23:14:58Z")

</div>

Oh, yeah, I forgot to show that you can use a BitStruct to parse strings  
according to your defined format:

Joel VanderWerf wrote:

> require 'bit-struct'
> 
> class C \< BitStruct  
> &nbsp;&nbsp;signed :foo, 32, "Something signed"  
> &nbsp;&nbsp;unsigned :bar, 32, "Something UNsigned"  
> end

&nbsp;&nbsp;c = C.new(socket.recv(...))

&nbsp;&nbsp;p c.foo

and so on.

> **···**
>
> --  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;vjoel : Joel VanderWerf : path berkeley edu : 510 665 3407

---

<div class="post-metadata">

**Author:** ![Robert\_Evans](https://avatars.discourse-cdn.com/v4/letter/r/9fc29f/32.png) [@Robert\_Evans](https://rubytalk.org/u/Robert_Evans)\
**Post date:** [15 November 2005 18:35 UTC](https://rubytalk.org/t/reading-a-signed-byte-in-network-byte-order/22464/7 "2005-11-15T18:35:06Z")

</div>

Hi David,

The only thing I worried about that was according to the PickAxe v.2 book, I is in native order. I thought that would be a problem since I am running this on unix boxes and windows boxes. Is that a true concern?

Thanks for your reply,  
Bob

> **···**
>
> On Nov 15, 2005, at 9:40 AM, David Balmain wrote:
> 
> > Hi Robert,
> > 
> > I'm probably missing something here, but how about this? It works for  
> > your tests at least.
> > 
> > def signed4(file)  
> > &nbsp;&nbsp;file.read(4).reverse.unpack('l')[0]  
> > end
> > 
> > Cheers,  
> > Dave
> > 
> > On 11/16/05, Robert Evans \<robert.evans@acm.org\> wrote:
> > 
> > > Hi,
> > > 
> > > So, I came up with a solution, and would be grateful for Ruby style  
> > > tips. It seemed a lot harder to do than it needed to be.
> > > 
> > > Any help appreciated.
> > > 
> > > Thanks,  
> > > Bob
> > > 
> > > The Tests:
> > > 
> > > class ByteReaderTest \< Test::Unit::TestCase
> > > 
> > > &nbsp;&nbsp;&nbsp;def test\_read\_signed4\_negative  
> > > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;negative = "" \<\< 0xF2 \<\< 0x34 \<\< 0x56 \<\< 0x78  
> > > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;assert\_equal -231451016, signed4(StringIO.new(negative))  
> > > &nbsp;&nbsp;&nbsp;end
> > > 
> > > &nbsp;&nbsp;&nbsp;def test\_read\_signed4\_positive  
> > > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;positive = "" \<\< 0x02 \<\< 0x34 \<\< 0x56 \<\< 0x78  
> > > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;assert\_equal 36984440, signed4(StringIO.new(positive))  
> > > &nbsp;&nbsp;&nbsp;end
> > > 
> > > end
> > > 
> > > The Solution:
> > > 
> > > def signed4(file)  
> > > &nbsp;&nbsp;&nbsp;bits = (file.read(4).unpack('B32'))[0]  
> > > &nbsp;&nbsp;&nbsp;if bits[0..0].eql? "0" # sign bit is positive  
> > > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;bits.to\_i(2)  
> > > &nbsp;&nbsp;&nbsp;else # sign bit is negative  
> > > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;compute\_negative\_number\_from(bits)  
> > > &nbsp;&nbsp;&nbsp;end  
> > > end
> > > 
> > > def compute\_negative\_number\_from(bits)  
> > > &nbsp;&nbsp;&nbsp;twos\_complement = flip(bits).join.to\_i(2) + 1  
> > > &nbsp;&nbsp;&nbsp;-1 \* twos\_complement  
> > > end
> > > 
> > > def flip(bits)  
> > > &nbsp;&nbsp;&nbsp;bits.scan(/\w/).collect { |bit| (bit.eql?("1")) ? "0" : "1" }  
> > > end
> > > 
> > > On Nov 14, 2005, at 3:07 PM, Robert Evans wrote:
> > > 
> > > > Hi,
> > > > 
> > > > In trying to read 4 bytes as a signed integer from an IO in big-  
> > > > endian order, is there already a utility to do this in Ruby? I  
> > > > notice unpack has lots of combinations already, but seemingly not  
> > > > one for this. Maybe I am just missing it?
> > > > 
> > > > Thanks,  
> > > > Bob Evans

---

<div class="post-metadata">

**Author:** ![Robert\_Evans](https://avatars.discourse-cdn.com/v4/letter/r/9fc29f/32.png) [@Robert\_Evans](https://rubytalk.org/u/Robert_Evans)\
**Post date:** [15 November 2005 18:37 UTC](https://rubytalk.org/t/reading-a-signed-byte-in-network-byte-order/22464/8 "2005-11-15T18:37:25Z")

</div>

Sweet. That's a very slick answer. Thanks.

Bob

> **···**
>
> On Nov 15, 2005, at 9:56 AM, Ara.T.Howard wrote:
> 
> > On Wed, 16 Nov 2005, Robert Evans wrote:
> > 
> > > Hi,
> > > 
> > > So, I came up with a solution, and would be grateful for Ruby style tips. It seemed a lot harder to do than it needed to be.
> > > 
> > > Any help appreciated.
> > > 
> > > Thanks,  
> > > Bob
> > > 
> > > The Tests:
> > > 
> > > class ByteReaderTest \< Test::Unit::TestCase
> > > 
> > > def test\_read\_signed4\_negative  
> > > &nbsp;&nbsp;&nbsp;negative = "" \<\< 0xF2 \<\< 0x34 \<\< 0x56 \<\< 0x78  
> > > &nbsp;&nbsp;&nbsp;assert\_equal -231451016, signed4(StringIO.new(negative))  
> > > end
> > > 
> > > def test\_read\_signed4\_positive  
> > > &nbsp;&nbsp;&nbsp;positive = "" \<\< 0x02 \<\< 0x34 \<\< 0x56 \<\< 0x78  
> > > &nbsp;&nbsp;&nbsp;assert\_equal 36984440, signed4(StringIO.new(positive))  
> > > end
> > > 
> > > end
> > > 
> > > The Solution:
> > > 
> > > def signed4(file)  
> > > bits = (file.read(4).unpack('B32'))[0]  
> > > if bits[0..0].eql? "0" # sign bit is positive  
> > > &nbsp;&nbsp;&nbsp;bits.to\_i(2)  
> > > else # sign bit is negative  
> > > &nbsp;&nbsp;&nbsp;compute\_negative\_number\_from(bits)  
> > > end  
> > > end
> > > 
> > > def compute\_negative\_number\_from(bits)  
> > > twos\_complement = flip(bits).join.to\_i(2) + 1  
> > > -1 \* twos\_complement  
> > > end
> > > 
> > > def flip(bits)  
> > > bits.scan(/\w/).collect { |bit| (bit.eql?("1")) ? "0" : "1" }  
> > > end
> > 
> > harp:~ \> cat a.rb  
> > require "test/unit"  
> > class ByteReaderTest \< Test::Unit::TestCase  
> > &nbsp;&nbsp;MAX\_POS = 2 \*\* 31 -1  
> > &nbsp;&nbsp;BIG\_ENDIAN = [42].pack('N') == [42].pack('i')  
> > &nbsp;&nbsp;def test\_read\_signed4\_positive  
> > &nbsp;&nbsp;&nbsp;&nbsp;positive = [0x02, 0x34, 0x56, 0x78].pack "c\*"  
> > &nbsp;&nbsp;&nbsp;&nbsp;assert\_equal 36984440, signed4(positive)  
> > &nbsp;&nbsp;end  
> > &nbsp;&nbsp;def test\_read\_signed4\_negative  
> > &nbsp;&nbsp;&nbsp;&nbsp;negative = [0xF2, 0x34, 0x56, 0x78].pack "c\*"  
> > &nbsp;&nbsp;&nbsp;&nbsp;assert\_equal -231451016, signed4(negative)  
> > &nbsp;&nbsp;end  
> > &nbsp;&nbsp;def signed4 buf  
> > &nbsp;&nbsp;&nbsp;&nbsp;buf = buf.read 4 if buf.respond\_to? "read"  
> > &nbsp;&nbsp;&nbsp;&nbsp;raise RangeError unless buf.size == 4  
> > &nbsp;&nbsp;&nbsp;&nbsp;n = buf.unpack('N').first  
> > &nbsp;&nbsp;&nbsp;&nbsp;if n \> MAX\_POS  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(BIG\_ENDIAN ? buf : buf.reverse).unpack('l').first  
> > &nbsp;&nbsp;&nbsp;&nbsp;else  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;n  
> > &nbsp;&nbsp;&nbsp;&nbsp;end  
> > &nbsp;&nbsp;end  
> > end
> > 
> > harp:~ \> ruby a.rb  
> > Loaded suite a  
> > Started  
> > ..  
> > Finished in 0.000583 seconds.
> > 
> > 2 tests, 2 assertions, 0 failures, 0 errors
> > 
> > # -a --
> > 
> > # \> ara [dot] t [dot] howard [at] gmail [dot] com \> all happiness comes from the desire for others to be happy. all misery \> comes from the desire for oneself to be happy. \> -- bodhicaryavatara
