drm_gem_object_put_unlocked(&obj->gem);
 }
 
-static dma_addr_t tegra_bo_pin(struct host1x_bo *bo, struct sg_table **sgt)
+static struct sg_table *tegra_bo_pin(struct device *dev, struct host1x_bo *bo,
+                                    dma_addr_t *phys)
 {
        struct tegra_bo *obj = host1x_to_tegra_bo(bo);
+       struct sg_table *sgt;
+       int err;
+
+       if (phys)
+               *phys = obj->iova;
 
-       *sgt = obj->sgt;
+       sgt = kzalloc(sizeof(*sgt), GFP_KERNEL);
+       if (!sgt)
+               return ERR_PTR(-ENOMEM);
 
-       return obj->iova;
+       if (obj->pages) {
+               err = sg_alloc_table_from_pages(sgt, obj->pages, obj->num_pages,
+                                               0, obj->gem.size, GFP_KERNEL);
+               if (err < 0)
+                       goto free;
+       } else {
+               err = dma_get_sgtable(dev, sgt, obj->vaddr, obj->iova,
+                                     obj->gem.size);
+               if (err < 0)
+                       goto free;
+       }
+
+       return sgt;
+
+free:
+       kfree(sgt);
+       return ERR_PTR(err);
 }
 
-static void tegra_bo_unpin(struct host1x_bo *bo, struct sg_table *sgt)
+static void tegra_bo_unpin(struct device *dev, struct sg_table *sgt)
 {
+       sg_free_table(sgt);
+       kfree(sgt);
 }
 
 static void *tegra_bo_mmap(struct host1x_bo *bo)
 
 
 static unsigned int pin_job(struct host1x *host, struct host1x_job *job)
 {
+       struct device *dev = job->client->dev;
        unsigned int i;
        int err;
 
                        goto unpin;
                }
 
-               phys_addr = host1x_bo_pin(reloc->target.bo, &sgt);
+               sgt = host1x_bo_pin(dev, reloc->target.bo, &phys_addr);
+               if (IS_ERR(sgt)) {
+                       err = PTR_ERR(sgt);
+                       goto unpin;
+               }
 
                job->addr_phys[job->num_unpins] = phys_addr;
                job->unpins[job->num_unpins].bo = reloc->target.bo;
                        goto unpin;
                }
 
-               phys_addr = host1x_bo_pin(g->bo, &sgt);
+               sgt = host1x_bo_pin(host->dev, g->bo, &phys_addr);
+               if (IS_ERR(sgt)) {
+                       err = PTR_ERR(sgt);
+                       goto unpin;
+               }
 
                if (!IS_ENABLED(CONFIG_TEGRA_HOST1X_FIREWALL) && host->domain) {
                        for_each_sg(sgt->sgl, sg, sgt->nents, j)
                                iova_pfn(&host->iova, job->addr_phys[i]));
                }
 
-               host1x_bo_unpin(unpin->bo, unpin->sgt);
+               host1x_bo_unpin(host->dev, unpin->bo, unpin->sgt);
                host1x_bo_put(unpin->bo);
        }
 
 
 struct host1x_bo_ops {
        struct host1x_bo *(*get)(struct host1x_bo *bo);
        void (*put)(struct host1x_bo *bo);
-       dma_addr_t (*pin)(struct host1x_bo *bo, struct sg_table **sgt);
-       void (*unpin)(struct host1x_bo *bo, struct sg_table *sgt);
+       struct sg_table *(*pin)(struct device *dev, struct host1x_bo *bo,
+                               dma_addr_t *phys);
+       void (*unpin)(struct device *dev, struct sg_table *sgt);
        void *(*mmap)(struct host1x_bo *bo);
        void (*munmap)(struct host1x_bo *bo, void *addr);
        void *(*kmap)(struct host1x_bo *bo, unsigned int pagenum);
        bo->ops->put(bo);
 }
 
-static inline dma_addr_t host1x_bo_pin(struct host1x_bo *bo,
-                                      struct sg_table **sgt)
+static inline struct sg_table *host1x_bo_pin(struct device *dev,
+                                            struct host1x_bo *bo,
+                                            dma_addr_t *phys)
 {
-       return bo->ops->pin(bo, sgt);
+       return bo->ops->pin(dev, bo, phys);
 }
 
-static inline void host1x_bo_unpin(struct host1x_bo *bo, struct sg_table *sgt)
+static inline void host1x_bo_unpin(struct device *dev, struct host1x_bo *bo,
+                                  struct sg_table *sgt)
 {
-       bo->ops->unpin(bo, sgt);
+       bo->ops->unpin(dev, sgt);
 }
 
 static inline void *host1x_bo_mmap(struct host1x_bo *bo)