Print this page
9642 PKCS#11 softtoken should use explicit_bzero
Reviewed by: Dan McDonald <danmcd@joyent.com>
Reviewed by: Alex Wilson <alex.wilson@joyent.com>

Split Close
Expand all
Collapse all
          --- old/usr/src/lib/pkcs11/pkcs11_softtoken/common/softKeystoreUtil.c
          +++ new/usr/src/lib/pkcs11/pkcs11_softtoken/common/softKeystoreUtil.c
↓ open down ↓ 12 lines elided ↑ open up ↑
  13   13   * When distributing Covered Code, include this CDDL HEADER in each
  14   14   * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15   15   * If applicable, add the following below this CDDL HEADER, with the
  16   16   * fields enclosed by brackets "[]" replaced with your own identifying
  17   17   * information: Portions Copyright [yyyy] [name of copyright owner]
  18   18   *
  19   19   * CDDL HEADER END
  20   20   */
  21   21  /*
  22   22   * Copyright (c) 2004, 2010, Oracle and/or its affiliates. All rights reserved.
       23 + * Copyright 2018, Joyent, Inc.
  23   24   */
  24   25  
  25   26  /*
  26   27   * Functions used for manipulating the keystore
  27   28   */
  28   29  
  29   30  #include <stdio.h>
  30   31  #include <stdlib.h>
  31   32  #include <errno.h>
  32   33  #include <sys/stat.h>
↓ open down ↓ 430 lines elided ↑ open up ↑
 463  464          }
 464  465  
 465  466          if (writen_nointr(fd, (void *)hashed_pin, hashed_pin_len)
 466  467              != hashed_pin_len) {
 467  468                  goto cleanup;
 468  469          }
 469  470  
 470  471          (void) lock_file(fd, B_FALSE, B_FALSE);
 471  472  
 472  473          (void) close(fd);
 473      -        if (hashed_pin_salt)
 474      -                free(hashed_pin_salt);
      474 +        freezero(hashed_pin_salt, hashed_pin_salt_len);
 475  475          return (0);
 476  476  
 477  477  cleanup:
 478  478          (void) lock_file(fd, B_FALSE, B_FALSE);
 479  479          (void) unlink(ks_desc_file);
 480  480          (void) close(fd);
 481  481          (void) rmdir(get_keystore_path());
 482  482          (void) rmdir(pub_obj_path);
 483  483          (void) rmdir(pri_obj_path);
 484  484          return (-1);
↓ open down ↓ 400 lines elided ↑ open up ↑
 885  885  
 886  886          hashed_pin_size = SWAP64(hashed_pin_size);
 887  887  
 888  888          *hashed_pin = malloc(hashed_pin_size + 1);
 889  889          if (*hashed_pin == NULL) {
 890  890                  return (CKR_HOST_MEMORY);
 891  891          }
 892  892  
 893  893          if ((readn_nointr(fd, *hashed_pin, hashed_pin_size))
 894  894              != (ssize_t)hashed_pin_size) {
 895      -                free(*hashed_pin);
      895 +                freezero(*hashed_pin, hashed_pin_size + 1);
 896  896                  *hashed_pin = NULL;
 897  897                  return (CKR_FUNCTION_FAILED);
 898  898          }
 899  899          (*hashed_pin)[hashed_pin_size] = '\0';
 900  900          return (CKR_OK);
 901  901  }
 902  902  
 903  903  
 904  904  /*
 905  905   *      FUNCTION: soft_keystore_lock
↓ open down ↓ 407 lines elided ↑ open up ↑
1313 1313          }
1314 1314  
1315 1315          if (read_obj_data(old_fd, (char **)&buf, &nread) != CKR_OK) {
1316 1316                  goto cleanup;
1317 1317          }
1318 1318  
1319 1319          /* decrypt data using old key */
1320 1320          decrypted_len = 0;
1321 1321          if (soft_keystore_crypt(enc_key, old_iv, B_FALSE, buf, nread,
1322 1322              NULL, &decrypted_len) != CKR_OK) {
1323      -                free(buf);
     1323 +                freezero(buf, nread);
1324 1324                  goto cleanup;
1325 1325          }
1326 1326  
1327 1327          decrypted_buf = malloc(decrypted_len);
1328 1328          if (decrypted_buf == NULL) {
1329      -                free(buf);
     1329 +                freezero(buf, nread);
1330 1330                  goto cleanup;
1331 1331          }
1332 1332  
1333 1333          if (soft_keystore_crypt(enc_key, old_iv, B_FALSE, buf, nread,
1334 1334              decrypted_buf, &decrypted_len) != CKR_OK) {
1335      -                free(buf);
1336      -                free(decrypted_buf);
1337      -                goto cleanup;
     1335 +                freezero(buf, nread);
     1336 +                freezero(decrypted_buf, decrypted_len);
1338 1337          }
1339 1338  
1340      -        free(buf);
     1339 +        freezero(buf, nread);
1341 1340  
1342 1341          /* re-encrypt with new key */
1343 1342          encrypted_len = 0;
1344 1343          if (soft_keystore_crypt(new_enc_key, iv, B_TRUE, decrypted_buf,
1345 1344              decrypted_len, NULL, &encrypted_len) != CKR_OK) {
1346      -                free(decrypted_buf);
     1345 +                freezero(decrypted_buf, decrypted_len);
1347 1346                  goto cleanup;
1348 1347          }
1349 1348  
1350 1349          buf = malloc(encrypted_len);
1351 1350          if (buf == NULL) {
1352      -                free(decrypted_buf);
     1351 +                freezero(decrypted_buf, decrypted_len);
1353 1352                  goto cleanup;
1354 1353          }
1355 1354  
1356 1355          if (soft_keystore_crypt(new_enc_key, iv, B_TRUE, decrypted_buf,
1357 1356              decrypted_len, buf, &encrypted_len) != CKR_OK) {
1358      -                free(buf);
1359      -                free(decrypted_buf);
     1357 +                freezero(buf, encrypted_len);
     1358 +                freezero(buf, decrypted_len);
1360 1359                  goto cleanup;
1361 1360          }
1362 1361  
1363      -        free(decrypted_buf);
     1362 +        freezero(decrypted_buf, decrypted_len);
1364 1363  
1365 1364          /* calculate hmac on re-encrypted data using new hmac key */
1366 1365          hmac_len = OBJ_HMAC_SIZE;
1367 1366          if (soft_keystore_hmac(new_hmac_key, B_TRUE, buf,
1368 1367              encrypted_len, hmac, &hmac_len) != CKR_OK) {
1369      -                free(buf);
     1368 +                freezero(buf, encrypted_len);
1370 1369                  goto cleanup;
1371 1370          }
1372 1371  
1373 1372          /* just for sanity check */
1374 1373          if (hmac_len != OBJ_HMAC_SIZE) {
1375      -                free(buf);
     1374 +                freezero(buf, encrypted_len);
1376 1375                  goto cleanup;
1377 1376          }
1378 1377  
1379 1378          /* write new hmac */
1380 1379          if (writen_nointr(new_fd, (char *)hmac, OBJ_HMAC_SIZE)
1381 1380              != OBJ_HMAC_SIZE) {
1382      -                free(buf);
     1381 +                freezero(buf, encrypted_len);
1383 1382                  goto cleanup;
1384 1383          }
1385 1384  
1386 1385          /* write re-encrypted buffer to temp file */
1387 1386          if (writen_nointr(new_fd, (void *)buf, encrypted_len)
1388 1387              != encrypted_len) {
1389      -                free(buf);
     1388 +                freezero(buf, encrypted_len);
1390 1389                  goto cleanup;
1391 1390          }
1392      -        free(buf);
     1391 +        freezero(buf, encrypted_len);
1393 1392          ret_val = 0;
1394 1393  
1395 1394  cleanup:
1396 1395          /* unlock the files */
1397 1396          (void) lock_file(old_fd, B_TRUE, B_FALSE);
1398 1397          (void) lock_file(new_fd, B_FALSE, B_FALSE);
1399 1398  
1400 1399          (void) close(old_fd);
1401 1400          (void) close(new_fd);
1402 1401          if (ret_val != 0) {
↓ open down ↓ 137 lines elided ↑ open up ↑
1540 1539                  /* PIN as never been set */
1541 1540                  CK_BYTE *new_crypt_salt = NULL, *new_hmac_salt = NULL;
1542 1541  
1543 1542                  pin_never_set = B_TRUE;
1544 1543                  if (soft_gen_crypt_key(newpin, &new_crypt_key, &new_crypt_salt)
1545 1544                      != CKR_OK) {
1546 1545                          goto cleanup;
1547 1546                  }
1548 1547                  if (writen_nointr(tmp_ks_fd, (void *)new_crypt_salt,
1549 1548                      KS_KEY_SALT_SIZE) != KS_KEY_SALT_SIZE) {
1550      -                        free(new_crypt_salt);
     1549 +                        freezero(new_crypt_salt,
     1550 +                            KS_KEY_SALT_SIZE);
1551 1551                          (void) soft_cleanup_object(new_crypt_key);
1552 1552                          goto cleanup;
1553 1553                  }
1554      -                free(new_crypt_salt);
     1554 +                freezero(new_crypt_salt, KS_KEY_SALT_SIZE);
1555 1555  
1556 1556                  if (soft_gen_hmac_key(newpin, &new_hmac_key, &new_hmac_salt)
1557 1557                      != CKR_OK) {
1558 1558                          (void) soft_cleanup_object(new_crypt_key);
1559 1559                          goto cleanup;
1560 1560                  }
1561 1561                  if (writen_nointr(tmp_ks_fd, (void *)new_hmac_salt,
1562 1562                      KS_HMAC_SALT_SIZE) != KS_HMAC_SALT_SIZE) {
1563      -                        free(new_hmac_salt);
     1563 +                        freezero(new_hmac_salt,
     1564 +                            KS_HMAC_SALT_SIZE);
1564 1565                          goto cleanup3;
1565 1566                  }
1566      -                free(new_hmac_salt);
     1567 +                freezero(new_hmac_salt, KS_HMAC_SALT_SIZE);
1567 1568          } else {
1568 1569                  if (soft_gen_crypt_key(newpin, &new_crypt_key,
1569 1570                      (CK_BYTE **)&crypt_salt) != CKR_OK) {
1570 1571                          goto cleanup;
1571 1572                  }
1572 1573                  /* no change to the encryption salt */
1573 1574                  if (writen_nointr(tmp_ks_fd, (void *)crypt_salt,
1574 1575                      KS_KEY_SALT_SIZE) != KS_KEY_SALT_SIZE) {
1575 1576                          (void) soft_cleanup_object(new_crypt_key);
1576 1577                          goto cleanup;
↓ open down ↓ 28 lines elided ↑ open up ↑
1605 1606  
1606 1607          hashed_pin_salt_length = SWAP64(hashed_pin_salt_length);
1607 1608  
1608 1609          hashed_pin_salt = malloc(hashed_pin_salt_length + 1);
1609 1610          if (hashed_pin_salt == NULL) {
1610 1611                  goto cleanup3;
1611 1612          }
1612 1613  
1613 1614          if ((readn_nointr(fd, hashed_pin_salt, hashed_pin_salt_length)) !=
1614 1615              (ssize_t)hashed_pin_salt_length) {
1615      -                free(hashed_pin_salt);
     1616 +                freezero(hashed_pin_salt,
     1617 +                    hashed_pin_salt_length + 1);
1616 1618                  goto cleanup3;
1617 1619          }
1618 1620  
1619 1621          if ((writen_nointr(tmp_ks_fd, hashed_pin_salt, hashed_pin_salt_length))
1620 1622              != (ssize_t)hashed_pin_salt_length) {
1621      -                free(hashed_pin_salt);
     1623 +                freezero(hashed_pin_salt,
     1624 +                    hashed_pin_salt_length + 1);
1622 1625                  goto cleanup3;
1623 1626          }
1624 1627  
1625 1628          hashed_pin_salt[hashed_pin_salt_length] = '\0';
1626 1629  
1627 1630          /* old hashed pin length and value can be ignored, generate new one */
1628 1631          if (soft_gen_hashed_pin(newpin, &new_hashed_pin,
1629 1632              &hashed_pin_salt) < 0) {
1630      -                free(hashed_pin_salt);
     1633 +                freezero(hashed_pin_salt,
     1634 +                    hashed_pin_salt_length + 1);
1631 1635                  goto cleanup3;
1632 1636          }
1633 1637  
1634      -        free(hashed_pin_salt);
     1638 +        freezero(hashed_pin_salt, hashed_pin_salt_length + 1);
1635 1639  
1636 1640          if (new_hashed_pin == NULL) {
1637 1641                  goto cleanup3;
1638 1642          }
1639 1643  
1640 1644          new_hashed_pin_len = strlen(new_hashed_pin);
1641 1645  
1642 1646          /* write new hashed pin length to file */
1643 1647          swaped_val = SWAP64(new_hashed_pin_len);
1644 1648          if (writen_nointr(tmp_ks_fd, (void *)&swaped_val,
↓ open down ↓ 111 lines elided ↑ open up ↑
1756 1760                  (void) soft_cleanup_object(new_crypt_key);
1757 1761                  (void) soft_cleanup_object(new_hmac_key);
1758 1762          }
1759 1763  
1760 1764  cleanup:
1761 1765          if (!lock_held) {
1762 1766                  if (lock_file(fd, B_FALSE, B_FALSE) < 0) {
1763 1767                          ret_val = 1;
1764 1768                  }
1765 1769          }
1766      -        if (crypt_salt != NULL) {
1767      -                free(crypt_salt);
1768      -        }
1769      -        if (hmac_salt != NULL) {
1770      -                free(hmac_salt);
1771      -        }
     1770 +        freezero(crypt_salt, KS_KEY_SALT_SIZE);
     1771 +        freezero(hmac_salt, KS_HMAC_SALT_SIZE);
1772 1772          (void) close(fd);
1773 1773          (void) close(tmp_ks_fd);
1774 1774          if (ret_val != 0) {
1775 1775                  (void) remove(tmp_ks_desc_name);
1776 1776          }
1777 1777          return (ret_val);
1778 1778  }
1779 1779  
1780 1780  /*
1781 1781   *      FUNCTION: soft_keystore_authpin
↓ open down ↓ 66 lines elided ↑ open up ↑
1848 1848              != CKR_OK) {
1849 1849                  goto cleanup;
1850 1850          }
1851 1851  
1852 1852          ret_val = 0;
1853 1853  
1854 1854  cleanup:
1855 1855          /* unlock the file */
1856 1856          (void) lock_file(fd, B_TRUE, B_FALSE);
1857 1857          (void) close(fd);
1858      -        if (crypt_salt != NULL) {
1859      -                free(crypt_salt);
1860      -        }
1861      -        if (hmac_salt != NULL) {
1862      -                free(hmac_salt);
1863      -        }
     1858 +        freezero(crypt_salt, KS_KEY_SALT_SIZE);
     1859 +        freezero(hmac_salt, KS_HMAC_SALT_SIZE);
1864 1860          return (ret_val);
1865 1861  }
1866 1862  
1867 1863  /*
1868      - *      FUNCTION: soft_keystore_get_objs
     1864 + *      FUNCTION: soft_keystore_get_objs
1869 1865   *
1870 1866   *      ARGUMENTS:
1871 1867   *
1872 1868   *              search_type: Specify type of objects to return.
1873 1869   *              lock_held: TRUE if the lock is held by caller.
1874 1870   *
1875 1871   *
1876 1872   *      RETURN VALUE:
1877 1873   *
1878 1874   *              NULL: if there are no object in the database.
↓ open down ↓ 94 lines elided ↑ open up ↑
1973 1969  cleanup:
1974 1970  
1975 1971          /* close the keystore description file */
1976 1972          (void) lock_file(ks_fd, B_TRUE, B_FALSE);
1977 1973          (void) close(ks_fd);
1978 1974  
1979 1975          /* free all the objects found before hitting the error */
1980 1976          tmp = *result_obj_list;
1981 1977          while (tmp) {
1982 1978                  *result_obj_list = tmp->next;
1983      -                free(tmp->buf);
     1979 +                freezero(tmp->buf, tmp->size);
1984 1980                  free(tmp);
1985 1981                  tmp = *result_obj_list;
1986 1982          }
1987 1983          *result_obj_list = NULL;
1988 1984          return (rv);
1989 1985  }
1990 1986  
1991 1987  
1992 1988  /*
1993 1989   *      FUNCTION: soft_keystore_get_single_obj
↓ open down ↓ 86 lines elided ↑ open up ↑
2080 2076                  obj->buf = buf;
2081 2077                  *return_obj = obj;
2082 2078          } else {
2083 2079  
2084 2080                  CK_ULONG out_len = 0, hmac_size;
2085 2081  
2086 2082                  /* verify HMAC of the object, make sure it matches */
2087 2083                  hmac_size = OBJ_HMAC_SIZE;
2088 2084                  if (soft_keystore_hmac(hmac_key, B_FALSE, buf,
2089 2085                      nread, obj_hmac, &hmac_size) != CKR_OK) {
2090      -                        free(buf);
     2086 +                        freezero(buf, nread);
2091 2087                          rv = CKR_FUNCTION_FAILED;
2092 2088                          goto cleanup;
2093 2089                  }
2094 2090  
2095 2091                  /* decrypt object */
2096 2092                  if (soft_keystore_crypt(enc_key, iv, B_FALSE, buf, nread,
2097 2093                      NULL, &out_len) != CKR_OK) {
2098      -                        free(buf);
     2094 +                        freezero(buf, nread);
2099 2095                          rv = CKR_FUNCTION_FAILED;
2100 2096                          goto cleanup;
2101 2097                  }
2102 2098  
2103 2099                  decrypted_buf = malloc(sizeof (uchar_t) * out_len);
2104 2100                  if (decrypted_buf == NULL) {
2105      -                        free(buf);
     2101 +                        freezero(buf, nread);
2106 2102                          rv = CKR_HOST_MEMORY;
2107 2103                          goto cleanup;
2108 2104                  }
2109 2105  
2110 2106                  if (soft_keystore_crypt(enc_key, iv, B_FALSE, buf, nread,
2111 2107                      decrypted_buf, &out_len) != CKR_OK) {
2112      -                        free(decrypted_buf);
2113      -                        free(buf);
     2108 +                        freezero(buf, nread);
     2109 +                        freezero(decrypted_buf, out_len);
2114 2110                          rv = CKR_FUNCTION_FAILED;
2115 2111                          goto cleanup;
2116 2112                  }
2117 2113  
2118 2114                  obj->size = out_len - MAXPATHLEN;
2119 2115  
2120 2116                  /*
2121 2117                   * decrypted buf here actually contains full path name of
2122 2118                   * object plus the actual data.  so, need to skip the
2123 2119                   * full pathname.
2124 2120                   * See prepare_data_for_encrypt() function in the file
2125 2121                   * to understand how and why the pathname is added.
2126 2122                   */
2127 2123                  obj->buf = malloc(sizeof (uchar_t) * (out_len - MAXPATHLEN));
2128 2124                  if (obj->buf == NULL) {
2129      -                        free(decrypted_buf);
2130      -                        free(buf);
     2125 +                        freezero(buf, nread);
     2126 +                        freezero(decrypted_buf, out_len);
2131 2127                          rv = CKR_HOST_MEMORY;
2132 2128                          goto cleanup;
2133 2129                  }
2134 2130                  (void) memcpy(obj->buf, decrypted_buf + MAXPATHLEN, obj->size);
2135      -                free(decrypted_buf);
2136      -                free(buf);
     2131 +                freezero(buf, nread);
     2132 +                freezero(decrypted_buf, out_len);
2137 2133                  *return_obj = obj;
2138 2134          }
2139 2135  
2140 2136  cleanup:
2141 2137  
2142 2138          if (rv != CKR_OK) {
2143 2139                  free(obj);
2144 2140          }
2145 2141  
2146 2142          /* unlock the file after reading */
↓ open down ↓ 1 lines elided ↑ open up ↑
2148 2144                  (void) lock_file(fd, B_TRUE, B_FALSE);
2149 2145          }
2150 2146  
2151 2147          (void) close(fd);
2152 2148  
2153 2149          return (rv);
2154 2150  }
2155 2151  
2156 2152  
2157 2153  /*
2158      - *      FUNCTION: soft_keystore_put_new_obj
     2154 + *      FUNCTION: soft_keystore_put_new_obj
2159 2155   *
2160 2156   *      ARGUMENTS:
2161 2157   *              buf: buffer containing un-encrypted data
2162 2158   *                   to be stored in keystore.
2163 2159   *              len: length of data
2164 2160   *              public:  TRUE if it is a public object,
2165 2161   *                       FALSE if it is private obj
2166 2162   *              lock_held: TRUE if the lock is held by caller.
2167 2163   *              keyhandle: pointer to object handle to
2168 2164   *                         receive keyhandle for new object
↓ open down ↓ 160 lines elided ↑ open up ↑
2329 2325                  CK_ULONG out_len = 0, prepared_len;
2330 2326  
2331 2327                  if (prepare_data_for_encrypt(obj_name, buf, len,
2332 2328                      &prepared_buf, &prepared_len) != 0) {
2333 2329                          goto cleanup2;
2334 2330                  }
2335 2331  
2336 2332                  if (soft_keystore_crypt(enc_key, iv,
2337 2333                      B_TRUE, prepared_buf, prepared_len,
2338 2334                      NULL, &out_len) != CKR_OK) {
2339      -                        free(prepared_buf);
     2335 +                        freezero(prepared_buf, prepared_len);
2340 2336                          goto cleanup2;
2341 2337                  }
2342 2338  
2343 2339                  encrypted_buf = malloc(out_len * sizeof (char));
2344 2340                  if (encrypted_buf == NULL) {
2345      -                        free(prepared_buf);
     2341 +                        freezero(prepared_buf, prepared_len);
2346 2342                          goto cleanup2;
2347 2343                  }
2348 2344  
2349 2345                  if (soft_keystore_crypt(enc_key, iv,
2350 2346                      B_TRUE, prepared_buf, prepared_len,
2351 2347                      encrypted_buf, &out_len) != CKR_OK) {
2352      -                        free(encrypted_buf);
2353      -                        free(prepared_buf);
     2348 +                        freezero(encrypted_buf, out_len);
     2349 +                        freezero(prepared_buf, prepared_len);
2354 2350                          goto cleanup2;
2355 2351                  }
2356      -                free(prepared_buf);
     2352 +                freezero(prepared_buf, prepared_len);
2357 2353  
2358 2354                  /* calculate HMAC of encrypted object */
2359 2355                  hmac_size = OBJ_HMAC_SIZE;
2360 2356                  if (soft_keystore_hmac(hmac_key, B_TRUE, encrypted_buf,
2361 2357                      out_len, obj_hmac, &hmac_size) != CKR_OK) {
2362      -                        free(encrypted_buf);
     2358 +                        freezero(encrypted_buf, out_len);
2363 2359                          goto cleanup2;
2364 2360                  }
2365 2361  
2366 2362                  if (hmac_size != OBJ_HMAC_SIZE) {
2367      -                        free(encrypted_buf);
     2363 +                        freezero(encrypted_buf, out_len);
2368 2364                          goto cleanup2;
2369 2365                  }
2370 2366  
2371 2367                  /* write hmac */
2372 2368                  if (writen_nointr(obj_fd, (void *)obj_hmac,
2373 2369                      sizeof (obj_hmac)) != sizeof (obj_hmac)) {
2374      -                        free(encrypted_buf);
     2370 +                        freezero(encrypted_buf, out_len);
2375 2371                          goto cleanup2;
2376 2372                  }
2377 2373  
2378 2374                  /* write encrypted object */
2379 2375                  if (writen_nointr(obj_fd, (void *)encrypted_buf, out_len)
2380 2376                      != out_len) {
2381      -                        free(encrypted_buf);
     2377 +                        freezero(encrypted_buf, out_len);
2382 2378                          goto cleanup2;
2383 2379                  }
2384 2380  
2385      -                free(encrypted_buf);
     2381 +                freezero(encrypted_buf, out_len);
2386 2382          }
2387 2383  
2388 2384  
2389 2385          (void) close(obj_fd);
2390 2386          (void) snprintf((char *)keyhandle->name, sizeof (keyhandle->name),
2391 2387              "obj%d", counter);
2392 2388          keyhandle->public = public;
2393 2389  
2394 2390          /*
2395 2391           * store new counter to temp keystore description file.
↓ open down ↓ 18 lines elided ↑ open up ↑
2414 2410          (void) rename(tmp_ks_desc_name, ks_desc_file);
2415 2411  
2416 2412          if (!lock_held) {
2417 2413                  /* release lock on description file */
2418 2414                  if (lock_file(fd, B_FALSE, B_FALSE) != 0) {
2419 2415                          (void) close(fd);
2420 2416                          return (-1);
2421 2417                  }
2422 2418          }
2423 2419          (void) close(fd);
     2420 +        explicit_bzero(obj_hmac, sizeof (obj_hmac));
     2421 +        explicit_bzero(iv, sizeof (iv));
2424 2422          return (0);
2425 2423  
2426 2424  cleanup2:
2427 2425  
2428 2426          /* remove object file.  No need to remove lock first */
2429 2427          (void) unlink(obj_name);
2430 2428  
2431 2429  cleanup:
2432 2430  
2433 2431          (void) close(tmp_ks_fd);
2434 2432          (void) remove(tmp_ks_desc_name);
2435 2433          if (!lock_held) {
2436 2434                  /* release lock on description file */
2437 2435                  (void) lock_file(fd, B_FALSE, B_FALSE);
2438 2436          }
2439 2437  
2440 2438          (void) close(fd);
     2439 +        explicit_bzero(obj_hmac, sizeof (obj_hmac));
     2440 +        explicit_bzero(iv, sizeof (iv));
2441 2441          return (-1);
2442 2442  }
2443 2443  
2444 2444  /*
2445 2445   *      FUNCTION: soft_keystore_modify_obj
2446 2446   *
2447 2447   *      ARGUMENTS:
2448 2448   *              ks_handle: handle of the key store object to be modified
2449 2449   *              buf: buffer containing un-encrypted data
2450 2450   *                   to be modified in keystore.
↓ open down ↓ 133 lines elided ↑ open up ↑
2584 2584  
2585 2585                  /* encrypt the data */
2586 2586                  if (soft_keystore_crypt(enc_key, iv, B_TRUE, prepared_buf,
2587 2587                      prepared_len, NULL, &out_len) != CKR_OK) {
2588 2588                          free(prepared_buf);
2589 2589                          goto cleanup2;
2590 2590                  }
2591 2591  
2592 2592                  encrypted_buf = malloc(out_len * sizeof (char));
2593 2593                  if (encrypted_buf == NULL) {
2594      -                        free(prepared_buf);
     2594 +                        freezero(prepared_buf, prepared_len);
2595 2595                          goto cleanup2;
2596 2596                  }
2597 2597  
2598 2598                  if (soft_keystore_crypt(enc_key, iv, B_TRUE, prepared_buf,
2599 2599                      prepared_len, encrypted_buf, &out_len) != CKR_OK) {
2600      -                        free(encrypted_buf);
2601      -                        free(prepared_buf);
     2600 +                        freezero(prepared_buf, prepared_len);
     2601 +                        freezero(encrypted_buf, out_len);
2602 2602                          goto cleanup2;
2603 2603                  }
2604 2604  
2605      -                free(prepared_buf);
     2605 +                freezero(prepared_buf, prepared_len);
2606 2606  
2607 2607                  /* calculate hmac on encrypted buf */
2608 2608                  hmac_size = OBJ_HMAC_SIZE;
2609 2609                  if (soft_keystore_hmac(hmac_key, B_TRUE, encrypted_buf,
2610 2610                      out_len, obj_hmac, &hmac_size) != CKR_OK) {
2611      -                        free(encrypted_buf);
     2611 +                        freezero(encrypted_buf, out_len);
2612 2612                          goto cleanup2;
2613 2613                  }
2614 2614  
2615 2615                  if (hmac_size != OBJ_HMAC_SIZE) {
2616      -                        free(encrypted_buf);
     2616 +                        freezero(encrypted_buf, out_len);
2617 2617                          goto cleanup2;
2618 2618                  }
2619 2619  
2620 2620                  if (writen_nointr(tmp_fd, (char *)obj_hmac, OBJ_HMAC_SIZE)
2621 2621                      != OBJ_HMAC_SIZE) {
2622      -                        free(encrypted_buf);
     2622 +                        freezero(encrypted_buf, out_len);
2623 2623                          goto cleanup2;
2624 2624                  }
2625 2625  
2626 2626                  if (writen_nointr(tmp_fd, (void *)encrypted_buf, out_len)
2627 2627                      != out_len) {
2628      -                        free(encrypted_buf);
     2628 +                        freezero(encrypted_buf, out_len);
2629 2629                          goto cleanup2;
2630 2630                  }
2631      -                free(encrypted_buf);
     2631 +                freezero(encrypted_buf, out_len);
2632 2632          }
2633 2633          (void) close(tmp_fd);
2634 2634  
2635 2635          /* rename updated temporary object file */
2636 2636          if (rename(tmp_name, orig_name) != 0) {
2637 2637                  (void) unlink(tmp_name);
2638 2638                  return (-1);
2639 2639          }
2640 2640  
2641 2641          /* rename updated keystore description file */
↓ open down ↓ 16 lines elided ↑ open up ↑
2658 2658          if (lock_file(ks_fd, B_FALSE, B_FALSE) != 0) {
2659 2659                  (void) close(ks_fd);
2660 2660                  (void) close(fd);
2661 2661                  return (-1);
2662 2662          }
2663 2663  
2664 2664          (void) close(ks_fd);
2665 2665  
2666 2666          (void) close(fd);
2667 2667  
     2668 +        explicit_bzero(iv, sizeof (iv));
     2669 +        explicit_bzero(obj_hmac, sizeof (obj_hmac));
2668 2670          return (0); /* All operations completed successfully */
2669 2671  
2670 2672  cleanup2:
2671 2673          (void) close(tmp_fd);
2672 2674          (void) remove(tmp_name);
2673 2675  
2674 2676  cleanup1:
2675 2677          (void) close(fd);
2676 2678  
2677 2679  cleanup:
2678 2680          /* unlock keystore description file */
2679 2681          (void) lock_file(ks_fd, B_FALSE, B_FALSE);
2680 2682          (void) close(ks_fd);
2681 2683          (void) remove(tmp_ks_name);
     2684 +        explicit_bzero(iv, sizeof (iv));
     2685 +        explicit_bzero(obj_hmac, sizeof (obj_hmac));
2682 2686          return (-1);
2683 2687  }
2684 2688  
2685 2689  /*
2686 2690   *      FUNCTION: soft_keystore_del_obj
2687 2691   *
2688 2692   *      ARGUMENTS:
2689 2693   *              ks_handle: handle of the key store object to be deleted
2690 2694   *              lock_held: TRUE if the lock is held by caller.
2691 2695   *
↓ open down ↓ 104 lines elided ↑ open up ↑
2796 2800          }
2797 2801          hashed_pin_salt_size = SWAP64(hashed_pin_salt_size);
2798 2802  
2799 2803          *salt = malloc(hashed_pin_salt_size + 1);
2800 2804          if (*salt == NULL) {
2801 2805                  goto cleanup;
2802 2806          }
2803 2807  
2804 2808          if ((readn_nointr(fd, *salt, hashed_pin_salt_size))
2805 2809              != (ssize_t)hashed_pin_salt_size) {
2806      -                free(*salt);
     2810 +                freezero(*salt, hashed_pin_salt_size + 1);
2807 2811                  goto cleanup;
2808 2812          }
2809 2813          (*salt)[hashed_pin_salt_size] = '\0';
2810 2814  
2811 2815          ret_val = 0;
2812 2816  
2813 2817  cleanup:
2814 2818          if (lock_file(fd, B_TRUE, B_FALSE) < 0) {
2815 2819                  ret_val = -1;
2816 2820          }
↓ open down ↓ 226 lines elided ↑ open up ↑
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX