Index: tests/test_amf3.py
===================================================================
--- tests/test_amf3.py	(revision 1154)
+++ tests/test_amf3.py	(working copy)
@@ -298,13 +298,21 @@
 
     def test_integer(self):
         self._run([(0, '\x04\x00')])
+        self._run([(0x35, '\x04\x35')])
         self._run([(0x7f, '\x04\x7f')])
         self._run([(0x80, '\x04\x81\x00')])
+        self._run([(0xd4, '\x04\x81\x54')])
         self._run([(0x3fff, '\x04\xff\x7f')])
         self._run([(0x4000, '\x04\x81\x80\x00')])
+        self._run([(0x1a53f, '\x04\x86\xca\x3f')])
         self._run([(0x1fffff, '\x04\xff\xff\x7f')])
         self._run([(0x200000, '\x04\x80\xc0\x80\x00')])
-        self._run([(0x3fffffff, '\x04\xff\xff\xff\xff')])
+        self._run([(-0x01, '\x04\xff\xff\xff\xff')])
+        self._run([(-0x2a, '\x04\xff\xff\xff\xd6')])
+        self._run([(0xfffffff, '\x04\xbf\xff\xff\xff')])
+        self._run([(-0x10000000, '\x04\xc0\x80\x80\x00')])
+        self._run([(0x10000000, '\x05\x41\xb0\x00\x00\x00\x00\x00\x00')])
+        self._run([(-0x10000001, '\x05\xc1\xb0\x00\x00\x01\x00\x00\x00')])
 
     def test_number(self):
         self._run([
@@ -618,14 +626,37 @@
 
     def test_integer(self):
         self._run([(0, '\x04\x00')])
+        self._run([(0x35, '\x04\x35')])
         self._run([(0x7f, '\x04\x7f')])
         self._run([(0x80, '\x04\x81\x00')])
+        self._run([(0xd4, '\x04\x81\x54')])
         self._run([(0x3fff, '\x04\xff\x7f')])
         self._run([(0x4000, '\x04\x81\x80\x00')])
+        self._run([(0x1a53f, '\x04\x86\xca\x3f')])
         self._run([(0x1fffff, '\x04\xff\xff\x7f')])
         self._run([(0x200000, '\x04\x80\xc0\x80\x00')])
-        self._run([(0x3fffffff, '\x04\xff\xff\xff\xff')])
+        self._run([(-0x01, '\x04\xff\xff\xff\xff')])
+        self._run([(-0x2a, '\x04\xff\xff\xff\xd6')])
+        self._run([(0xfffffff, '\x04\xbf\xff\xff\xff')])
+        self._run([(-0x10000000, '\x04\xc0\x80\x80\x00')])
 
+    def test_unsignedInteger(self):
+        tests = [
+            (0, '\x00'),
+            (0x7f, '\x7f'),
+            (0x80, '\x81\x00'),
+            (0x3fff, '\xff\x7f'),
+            (0x4000, '\x81\x80\x00'),
+            (0x1fffff, '\xff\xff\x7f'),
+            (0x200000, '\x80\xc0\x80\x00'),
+            (0x3fffffff, '\xff\xff\xff\xff')
+        ]
+        for n,s in tests:
+            self.buf.truncate(0)
+            self.buf.write(s)
+            self.buf.seek(0)
+            self.assertEqual(self.decoder.readUnsignedInteger(), n)
+
     def test_infinites(self):
         import fpconst
 
Index: amf3.py
===================================================================
--- amf3.py	(revision 1154)
+++ amf3.py	(working copy)
@@ -860,7 +860,7 @@
         ASTypes.NULL:       'readNull',
         ASTypes.BOOL_FALSE: 'readBoolFalse',
         ASTypes.BOOL_TRUE:  'readBoolTrue',
-        ASTypes.INTEGER:    'readInteger',
+        ASTypes.INTEGER:    'readSignedInteger',
         ASTypes.NUMBER:     'readNumber',
         ASTypes.STRING:     'readString',
         ASTypes.XML:        'readXML',
@@ -925,8 +925,20 @@
         """
         return self.stream.read_double()
 
-    def readInteger(self):
+    def readUnsignedInteger(self):
         """
+        Reads and returns a signed integer from the stream.
+        """
+        return self.readInteger(False)
+
+    def readSignedInteger(self):
+        """
+        Reads and returns a signed integer from the stream.
+        """
+        return self.readInteger(True)
+
+    def readInteger(self, signed=False):
+        """
         Reads and returns an integer from the stream.
 
         @see: U{Parsing integers on OSFlash
@@ -950,8 +962,11 @@
             result |= b
 
             if result & 0x10000000 != 0:
-                result <<= 1
-                result += 1
+                if signed:
+                    result -= 0x20000000
+                else:
+                    result <<= 1
+                    result += 1
 
         return result
 
@@ -963,7 +978,7 @@
         @param use_references:
         """
         def readLength():
-            x = self.readInteger()
+            x = self.readUnsignedInteger()
 
             return (x >> 1, x & REFERENCE_BIT == 0)
 
@@ -986,7 +1001,7 @@
 
         The timezone is ignored as the date is always in UTC.
         """
-        ref = self.readInteger()
+        ref = self.readUnsignedInteger()
 
         if ref & REFERENCE_BIT == 0:
             return self.context.getObject(ref >> 1)
@@ -1009,7 +1024,7 @@
         @see: U{Docuverse blog
         <http://www.docuverse.com/blog/donpark/2007/05/14/flash-9-amf3-bug>}
         """
-        size = self.readInteger()
+        size = self.readUnsignedInteger()
 
         if size & REFERENCE_BIT == 0:
             return self.context.getObject(size >> 1)
@@ -1083,7 +1098,7 @@
                 setattr(obj, attr, self.readElement())
                 attr = self.readString()
 
-        ref = self.readInteger()
+        ref = self.readUnsignedInteger()
 
         if ref & REFERENCE_BIT == 0:
             return self.context.getObject(ref >> 1)
@@ -1129,7 +1144,7 @@
         @type legacy: C{bool}
         @param legacy: The read XML is in 'legacy' format.
         """
-        ref = self.readInteger()
+        ref = self.readUnsignedInteger()
 
         if ref & REFERENCE_BIT == 0:
             return self.context.getObject(ref >> 1)
@@ -1171,7 +1186,7 @@
         @see: L{ByteArray}
         @note: This is not supported in ActionScript 1.0 and 2.0.
         """
-        ref = self.readInteger()
+        ref = self.readUnsignedInteger()
 
         if ref & REFERENCE_BIT == 0:
             return self.context.getObject(ref >> 1)
@@ -1306,7 +1321,7 @@
         @type   use_references: C{bool}
         @param  use_references:
         """
-        if n > 0x3fffffff:
+        if n & 0xf0000000 not in [0, 0xf0000000]:
             self.writeNumber(n)
 
             return
@@ -1716,12 +1731,15 @@
     return buf
 
 def _encode_int(n):
-    if n > 0x40000000:
+    if n & 0xf0000000 not in [0, 0xf0000000]:
         raise ValueError, "Out of range"
 
     bytes = ''
     real_value = None
 
+    if n < 0:
+        n += 0x20000000
+
     if n > 0x1fffff:
         real_value = n
         n >>= 1
