tmpfs: Allow kmalloc from M_TMPFSNAME zone to return NULL; handle null cases.
authorVenkatesh Srinivas <me@endeavour.zapto.org>
Wed, 25 Aug 2010 03:03:34 +0000 (20:03 -0700)
committerVenkatesh Srinivas <me@endeavour.zapto.org>
Wed, 25 Aug 2010 03:03:34 +0000 (20:03 -0700)
tmpfs now survives fsstress without panicing the system.

sys/vfs/tmpfs/tmpfs_subr.c
sys/vfs/tmpfs/tmpfs_vnops.c

index 564c8b7..8f286e4 100644 (file)
@@ -126,6 +126,7 @@ tmpfs_alloc_node(struct tmpfs_mount *tmp, enum vtype type,
        case VCHR:
                rdev = makeudev(rmajor, rminor);
                if (rdev == NOUDEV) {
+                       objcache_put(tmp->tm_node_pool, nnode);
                        return(EINVAL);
                }
                nnode->tn_rdev = rdev;
@@ -155,7 +156,11 @@ tmpfs_alloc_node(struct tmpfs_mount *tmp, enum vtype type,
        case VLNK:
                nnode->tn_size = strlen(target);
                nnode->tn_link = kmalloc(nnode->tn_size + 1, M_TMPFSNAME,
-                                        M_WAITOK);
+                                        M_WAITOK | M_NULLOK);
+               if (nnode->tn_link == NULL) {
+                       objcache_put(tmp->tm_node_pool, nnode);
+                       return (ENOSPC);
+               }
                bcopy(target, nnode->tn_link, nnode->tn_size);
                nnode->tn_link[nnode->tn_size] = '\0';
                break;
@@ -315,9 +320,13 @@ tmpfs_alloc_dirent(struct tmpfs_mount *tmp, struct tmpfs_node *node,
 {
        struct tmpfs_dirent *nde;
 
-
-       nde = (struct tmpfs_dirent *)objcache_get(tmp->tm_dirent_pool, M_WAITOK);
-       nde->td_name = kmalloc(len + 1, M_TMPFSNAME, M_WAITOK);
+       nde = objcache_get(tmp->tm_dirent_pool, M_WAITOK);
+       nde->td_name = kmalloc(len + 1, M_TMPFSNAME, M_WAITOK | M_NULLOK);
+       if (nde->td_name == NULL) {
+               objcache_put(tmp->tm_dirent_pool, nde);
+               *de = NULL;
+               return (ENOSPC);
+       }
        nde->td_namelen = len;
        bcopy(name, nde->td_name, len);
        nde->td_name[len] = '\0';
index a582618..9dfae26 100644 (file)
@@ -937,7 +937,12 @@ tmpfs_nrename(struct vop_nrename_args *v)
         */
        if (fncp->nc_nlen != tncp->nc_nlen ||
            bcmp(fncp->nc_name, tncp->nc_name, fncp->nc_nlen) != 0) {
-               newname = kmalloc(tncp->nc_nlen + 1, M_TMPFSNAME, M_WAITOK);
+               newname = kmalloc(tncp->nc_nlen + 1, M_TMPFSNAME, 
+                                 M_WAITOK | M_NULLOK);
+               if (newname == NULL) {
+                       error = ENOSPC;
+                       goto out_locked;
+               }
                bcopy(tncp->nc_name, newname, tncp->nc_nlen);
                newname[tncp->nc_nlen] = '\0';
        } else {