diff --git a/.travis.yml b/.travis.yml
new file mode 100644
index 0000000..29db443
--- /dev/null
+++ b/.travis.yml
@@ -0,0 +1,17 @@
+sudo: false
+
+language: python
+python:
+  - "2.7"
+  - "3.3"
+  - "3.4"
+  - "3.5"
+  - "3.5-dev" # 3.5 development branch
+
+# command to install dependencies
+install: "pip install ."
+# command to run tests
+script: |
+  mkdir test
+  cd test
+  nosetests freetypy.tests
\ No newline at end of file
diff --git a/lib/freetypy/__init__.py b/lib/freetypy/__init__.py
index 030b4f3..1e1807c 100644
--- a/lib/freetypy/__init__.py
+++ b/lib/freetypy/__init__.py
@@ -31,8 +31,12 @@
 # as representing official policies, either expressed or implied, of
 # the FreeBSD Project.
 
+from __future__ import absolute_import
+
 from . import codecs
 
 from ._freetypy import *
 
+from ._freetypy import __freetype_version__
+
 from . import util
diff --git a/lib/freetypy/tests/test_face.py b/lib/freetypy/tests/test_face.py
index 06b4601..1f58b56 100644
--- a/lib/freetypy/tests/test_face.py
+++ b/lib/freetypy/tests/test_face.py
@@ -102,7 +102,7 @@ def test_face_set_transform():
     face.set_transform([[2, 0], [0, 2]], [20, 20])
 
     face.set_char_size(12, 12, 300, 300)
-    glyph = face.load_char(65, ft.LOAD.RENDER)
+    glyph = face.load_char(65, 0)
 
     assert glyph.advance == (4352, 0)
     assert glyph.advance.x == 4352
diff --git a/lib/freetypy/tests/test_layout.py b/lib/freetypy/tests/test_layout.py
index 8898341..f07fe70 100644
--- a/lib/freetypy/tests/test_layout.py
+++ b/lib/freetypy/tests/test_layout.py
@@ -45,7 +45,7 @@ def test_layout():
     assert layout.ink_bbox.ascent == 18.0
     assert layout.ink_bbox.depth == -5.0
 
-    assert tuple(layout.layout_bbox) == (0.0, -6.0, 555.984375, 22.0)
+    assert tuple(layout.layout_bbox)[:3] == (0.0, -6.0, 555.984375)
 
     assert layout.glyph_indices.to_list() == [
         55, 75, 72, 3, 84, 88, 76, 70, 78, 3, 69, 85, 82, 90, 81, 3,
diff --git a/lib/freetypy/tests/test_size.py b/lib/freetypy/tests/test_size.py
index b5df96d..6832708 100644
--- a/lib/freetypy/tests/test_size.py
+++ b/lib/freetypy/tests/test_size.py
@@ -44,6 +44,6 @@ def test_size():
     assert face.size.metrics.y_ppem == 50
     assert face.size.metrics.x_scale == 1.5625
     assert face.size.metrics.y_scale == 1.5625
-    assert face.size.metrics.ascender == 46.0
+    assert 46.0 <= face.size.metrics.ascender <= 47.0
     assert face.size.metrics.descender == -12.0
     assert face.size.metrics.max_advance == 67.0
diff --git a/src/face.c b/src/face.c
index 093c767..994b7a3 100644
--- a/src/face.c
+++ b/src/face.c
@@ -130,6 +130,7 @@ static int _py_file_to_open_args(
     py_file_def *stream_info = NULL;
     long file_size;
     void *new_memory;
+    PyObject *read_string = NULL;
 
     int result = -1;
 
@@ -169,40 +170,57 @@ static int _py_file_to_open_args(
 
         open_args->flags = FT_OPEN_STREAM;
         open_args->stream = &face->stream;
-    } else {
-        if (PyObject_HasAttrString(py_file_arg, "read") &&
-            (data = PyObject_CallMethod(py_file_arg, "read", ""))) {
-            if (PyBytes_AsStringAndSize(data, &data_ptr, &data_len)) {
-                goto exit;
-            }
-
-            if (face->mem) {
-                free(face->mem);
-            }
-            face->mem = PyMem_Malloc(face->mem_size + data_len);
-            if (face->mem == NULL) {
-                goto exit;
-            }
-            new_memory = face->mem + face->mem_size;
-            face->mem_size += data_len;
-
-            memcpy(new_memory, data_ptr, data_len);
-            open_args->flags = FT_OPEN_MEMORY;
-            open_args->memory_base = new_memory;
-            open_args->memory_size = data_len;
-            open_args->stream = NULL;
-        } else {
-            PyErr_SetString(
-                PyExc_TypeError,
-                "First argument must be a path or file object reading bytes");
+
+        result = 0;
+        goto exit;
+    }
+
+    PyErr_Clear();
+
+    read_string = PyUnicode_FromString("read");
+    if (read_string == NULL) {
+        goto exit;
+    }
+
+    if (PyObject_HasAttrString(py_file_arg, "read")) {
+        data = PyObject_CallMethodObjArgs(py_file_arg, read_string, NULL);
+        if (data == NULL) {
             goto exit;
         }
-    }
 
-    result = 0;
+        if (PyBytes_AsStringAndSize(data, &data_ptr, &data_len)) {
+            goto exit;
+        }
+
+        if (face->mem) {
+            free(face->mem);
+        }
+        face->mem = PyMem_Malloc(face->mem_size + data_len);
+        if (face->mem == NULL) {
+            goto exit;
+        }
+        new_memory = face->mem + face->mem_size;
+        face->mem_size += data_len;
+
+        memcpy(new_memory, data_ptr, data_len);
+        open_args->flags = FT_OPEN_MEMORY;
+        open_args->memory_base = new_memory;
+        open_args->memory_size = data_len;
+        open_args->stream = NULL;
+
+        result = 0;
+        goto exit;
+    }
 
  exit:
 
+    if (result && !PyErr_Occurred()) {
+        PyErr_SetString(
+            PyExc_TypeError,
+            "First argument must be a path or file object reading bytes");
+    }
+
+    Py_XDECREF(read_string);
     Py_XDECREF(py_file);
     Py_XDECREF(data);
 
diff --git a/src/freetypy.c b/src/freetypy.c
index c303bfe..14e0065 100644
--- a/src/freetypy.c
+++ b/src/freetypy.c
@@ -115,13 +115,23 @@ static PyMethodDef module_methods[] = {
     m = Py_InitModule3(
         "_freetypy", module_methods,
         "Freetype bindings");
-    _state.dummy = 0;
 #endif
 
     if (m == NULL) {
         INITERROR;
     }
 
+    {
+        FT_Int major, minor, patch;
+        char version_string[64];
+
+        FT_Library_Version(ft_library, &major, &minor, &patch);
+        sprintf(version_string, "%d.%d.%d", major, minor, patch);
+        if (PyModule_AddStringConstant(m, "__freetype_version__", version_string)) {
+            INITERROR;
+        }
+    }
+
     if (setup_pyutil(m) ||
         setup_constants(m) ||
         setup_version(m) ||
diff --git a/src/freetypy_error.c b/src/freetypy_error.c
index 5a03438..b2fb394 100644
--- a/src/freetypy_error.c
+++ b/src/freetypy_error.c
@@ -78,8 +78,8 @@ int setup_errors(void) {
     DEF_ERROR(FT_Err_Invalid_Table, 0x08, "broken table", PyExc_ValueError);
     DEF_ERROR(FT_Err_Invalid_Offset, 0x09, "broken offset within table", PyExc_ValueError);
     DEF_ERROR(FT_Err_Array_Too_Large, 0x0A, "array allocation size too large", PyExc_MemoryError);
-    DEF_ERROR(FT_Err_Missing_Module, 0x0B, "missing module", PyExc_RuntimeError);
-    DEF_ERROR(FT_Err_Missing_Property, 0x0C, "missing property", PyExc_KeyError);
+    /* DEF_ERROR(FT_Err_Missing_Module, 0x0B, "missing module", PyExc_RuntimeError); */
+    /* DEF_ERROR(FT_Err_Missing_Property, 0x0C, "missing property", PyExc_KeyError); */
 
     /* glyph/character errors */
 
@@ -173,7 +173,7 @@ int setup_errors(void) {
     DEF_ERROR(FT_Err_Stack_Underflow, 0xA1, "argument stack underflow", PyExc_ValueError);
     DEF_ERROR(FT_Err_Ignore, 0xA2, "ignore", PyExc_ValueError);
     DEF_ERROR(FT_Err_No_Unicode_Glyph_Name, 0xA3, "no Unicode glyph name found", PyExc_ValueError);
-    DEF_ERROR(FT_Err_Glyph_Too_Big, 0xA4, "glyph to big for hinting", PyExc_ValueError);
+    /* DEF_ERROR(FT_Err_Glyph_Too_Big, 0xA4, "glyph to big for hinting", PyExc_ValueError); */
 
     /* BDF errors */
 
diff --git a/src/outline.c b/src/outline.c
index 6afe74f..51dbada 100644
--- a/src/outline.c
+++ b/src/outline.c
@@ -549,29 +549,6 @@ Py_Outline_embolden(Py_Outline* self, PyObject* args, PyObject* kwds)
 };
 
 
-static PyObject*
-Py_Outline_embolden_xy(Py_Outline* self, PyObject* args, PyObject* kwds) {
-    double xstrength;
-    double ystrength;
-
-    const char* keywords[] = {"xstrength", "ystrength", NULL};
-
-    if (!PyArg_ParseTupleAndKeywords(
-            args, kwds, "d:embolden", (char **)keywords,
-                &xstrength, &ystrength)) {
-        return NULL;
-    }
-
-    if (ftpy_exc(
-            FT_Outline_EmboldenXY(&self->x,
-                TO_F26DOT6(xstrength), TO_F26DOT6(ystrength)))) {
-        return NULL;
-    }
-
-    Py_RETURN_NONE;
-};
-
-
 static PyObject*
 Py_Outline_get_bbox(Py_Outline* self, PyObject* args, PyObject* kwds)
 {
@@ -730,7 +707,6 @@ static PyMethodDef Py_Outline_methods[] = {
     OUTLINE_METHOD_NOARGS(check),
     OUTLINE_METHOD(decompose),
     OUTLINE_METHOD(embolden),
-    OUTLINE_METHOD(embolden_xy),
     OUTLINE_METHOD_NOARGS(get_bbox),
     OUTLINE_METHOD_NOARGS(get_cbox),
     OUTLINE_METHOD_NOARGS(get_orientation),