* allocate new zcomp_strm structure with ->private initialized by
  * backend, return NULL on error
  */
-static struct zcomp_strm *zcomp_strm_alloc(struct zcomp *comp)
+static struct zcomp_strm *zcomp_strm_alloc(struct zcomp *comp, gfp_t flags)
 {
-       struct zcomp_strm *zstrm = kmalloc(sizeof(*zstrm), GFP_NOIO);
+       struct zcomp_strm *zstrm = kmalloc(sizeof(*zstrm), flags);
        if (!zstrm)
                return NULL;
 
-       zstrm->private = comp->backend->create();
+       zstrm->private = comp->backend->create(flags);
        /*
         * allocate 2 pages. 1 for compressed data, plus 1 extra for the
         * case when compressed size is larger than the original one
         */
-       zstrm->buffer = (void *)__get_free_pages(GFP_NOIO | __GFP_ZERO, 1);
+       zstrm->buffer = (void *)__get_free_pages(flags | __GFP_ZERO, 1);
        if (!zstrm->private || !zstrm->buffer) {
                zcomp_strm_free(comp, zstrm);
                zstrm = NULL;
                /* allocate new zstrm stream */
                zs->avail_strm++;
                spin_unlock(&zs->strm_lock);
-
-               zstrm = zcomp_strm_alloc(comp);
+               /*
+                * This function can be called in swapout/fs write path
+                * so we can't use GFP_FS|IO. And it assumes we already
+                * have at least one stream in zram initialization so we
+                * don't do best effort to allocate more stream in here.
+                * A default stream will work well without further multiple
+                * streams. That's why we use NORETRY | NOWARN.
+                */
+               zstrm = zcomp_strm_alloc(comp, GFP_NOIO | __GFP_NORETRY |
+                                       __GFP_NOWARN);
                if (!zstrm) {
                        spin_lock(&zs->strm_lock);
                        zs->avail_strm--;
        zs->max_strm = max_strm;
        zs->avail_strm = 1;
 
-       zstrm = zcomp_strm_alloc(comp);
+       zstrm = zcomp_strm_alloc(comp, GFP_KERNEL);
        if (!zstrm) {
                kfree(zs);
                return -ENOMEM;
 
        comp->stream = zs;
        mutex_init(&zs->strm_lock);
-       zs->zstrm = zcomp_strm_alloc(comp);
+       zs->zstrm = zcomp_strm_alloc(comp, GFP_KERNEL);
        if (!zs->zstrm) {
                kfree(zs);
                return -ENOMEM;
 
 
 #include "zcomp_lz4.h"
 
-static void *zcomp_lz4_create(void)
+static void *zcomp_lz4_create(gfp_t flags)
 {
        void *ret;
 
-       /*
-        * This function can be called in swapout/fs write path
-        * so we can't use GFP_FS|IO. And it assumes we already
-        * have at least one stream in zram initialization so we
-        * don't do best effort to allocate more stream in here.
-        * A default stream will work well without further multiple
-        * streams. That's why we use NORETRY | NOWARN.
-        */
-       ret = kzalloc(LZ4_MEM_COMPRESS, GFP_NOIO | __GFP_NORETRY |
-                                       __GFP_NOWARN);
+       ret = kzalloc(LZ4_MEM_COMPRESS, flags);
        if (!ret)
                ret = __vmalloc(LZ4_MEM_COMPRESS,
-                               GFP_NOIO | __GFP_NORETRY | __GFP_NOWARN |
-                               __GFP_ZERO | __GFP_HIGHMEM,
+                               flags | __GFP_ZERO | __GFP_HIGHMEM,
                                PAGE_KERNEL);
        return ret;
 }
 
 
 #include "zcomp_lzo.h"
 
-static void *lzo_create(void)
+static void *lzo_create(gfp_t flags)
 {
        void *ret;
 
-       /*
-        * This function can be called in swapout/fs write path
-        * so we can't use GFP_FS|IO. And it assumes we already
-        * have at least one stream in zram initialization so we
-        * don't do best effort to allocate more stream in here.
-        * A default stream will work well without further multiple
-        * streams. That's why we use NORETRY | NOWARN.
-        */
-       ret = kzalloc(LZO1X_MEM_COMPRESS, GFP_NOIO | __GFP_NORETRY |
-                                       __GFP_NOWARN);
+       ret = kzalloc(LZO1X_MEM_COMPRESS, flags);
        if (!ret)
                ret = __vmalloc(LZO1X_MEM_COMPRESS,
-                               GFP_NOIO | __GFP_NORETRY | __GFP_NOWARN |
-                               __GFP_ZERO | __GFP_HIGHMEM,
+                               flags | __GFP_ZERO | __GFP_HIGHMEM,
                                PAGE_KERNEL);
        return ret;
 }