Print this page
OS-4335 ipadm_door_call should work in a branded zone without chroot
OS-4336 ipmgmtd should work in a branded zone without chroot
Reviewed by: Robert Mustacchi <rm@joyent.com>

Split Close
Expand all
Collapse all
          --- old/usr/src/cmd/cmd-inet/lib/ipmgmtd/ipmgmt_persist.c
          +++ new/usr/src/cmd/cmd-inet/lib/ipmgmtd/ipmgmt_persist.c
↓ open down ↓ 13 lines elided ↑ open up ↑
  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  /*
  23   23   * Copyright (c) 2010, Oracle and/or its affiliates. All rights reserved.
       24 + * Copyright 2015 Joyent, Inc.
  24   25   * Copyright 2016 Argo Technologie SA.
  25   26   */
  26   27  
  27   28  /*
  28   29   * Contains DB walker functions, which are of type `db_wfunc_t';
  29   30   *
  30   31   * typedef boolean_t db_wfunc_t(void *cbarg, nvlist_t *db_nvl, char *buf,
  31   32   *                              size_t bufsize, int *errp);
  32   33   *
  33   34   * ipadm_rw_db() walks through the data store, one line at a time and calls
↓ open down ↓ 343 lines elided ↑ open up ↑
 377  378   * really a rare occurrence now that we don't support UFS root filesystems
 378  379   * any longer. This function will periodically attempt to write the
 379  380   * configuration back to its location on the root filesystem. Success
 380  381   * will indicate that the filesystem is no longer read-only.
 381  382   */
 382  383  /* ARGSUSED */
 383  384  static void *
 384  385  ipmgmt_db_restore_thread(void *arg)
 385  386  {
 386  387          int err;
      388 +        char confpath[MAXPATHLEN];
      389 +        char tmpconfpath[MAXPATHLEN];
 387  390  
      391 +        ipmgmt_path(IPADM_PATH_DB, confpath, sizeof (confpath));
      392 +        ipmgmt_path(IPADM_PATH_VOL_DB, tmpconfpath, sizeof (tmpconfpath));
      393 +
 388  394          for (;;) {
 389  395                  (void) sleep(5);
 390  396                  (void) pthread_rwlock_wrlock(&ipmgmt_dbconf_lock);
 391  397                  if (!ipmgmt_rdonly_root)
 392  398                          break;
 393      -                err = ipmgmt_cpfile(IPADM_VOL_DB_FILE, IPADM_DB_FILE, B_FALSE);
      399 +                err = ipmgmt_cpfile(tmpconfpath, confpath, B_FALSE);
 394  400                  if (err == 0) {
 395  401                          ipmgmt_rdonly_root = B_FALSE;
 396  402                          break;
 397  403                  }
 398  404                  (void) pthread_rwlock_unlock(&ipmgmt_dbconf_lock);
 399  405          }
 400  406          (void) pthread_rwlock_unlock(&ipmgmt_dbconf_lock);
 401  407          return (NULL);
 402  408  }
 403  409  
↓ open down ↓ 11 lines elided ↑ open up ↑
 415  421   * ipmgmt_db_restore_thread().
 416  422   */
 417  423  extern int
 418  424  ipmgmt_db_walk(db_wfunc_t *db_walk_func, void *db_warg, ipadm_db_op_t db_op)
 419  425  {
 420  426          int             err;
 421  427          boolean_t       writeop;
 422  428          mode_t          mode;
 423  429          pthread_t       tid;
 424  430          pthread_attr_t  attr;
      431 +        char            confpath[MAXPATHLEN];
      432 +        char            tmpconfpath[MAXPATHLEN];
 425  433  
      434 +        ipmgmt_path(IPADM_PATH_DB, confpath, sizeof (confpath));
      435 +        ipmgmt_path(IPADM_PATH_VOL_DB, tmpconfpath, sizeof (tmpconfpath));
      436 +
 426  437          writeop = (db_op != IPADM_DB_READ);
 427  438          if (writeop) {
 428  439                  (void) pthread_rwlock_wrlock(&ipmgmt_dbconf_lock);
 429  440                  mode = IPADM_FILE_MODE;
 430  441          } else {
 431  442                  (void) pthread_rwlock_rdlock(&ipmgmt_dbconf_lock);
 432  443                  mode = 0;
 433  444          }
 434  445  
 435  446          /*
 436  447           * Did a previous write attempt fail? If so, don't even try to
 437      -         * read/write to IPADM_DB_FILE.
      448 +         * read/write to the permanent configuration file.
 438  449           */
 439  450          if (!ipmgmt_rdonly_root) {
 440      -                err = ipadm_rw_db(db_walk_func, db_warg, IPADM_DB_FILE,
 441      -                    mode, db_op);
      451 +                err = ipadm_rw_db(db_walk_func, db_warg, confpath, mode, db_op);
 442  452                  if (err != EROFS)
 443  453                          goto done;
 444  454          }
 445  455  
 446  456          /*
 447  457           * If we haven't already copied the file to the volatile
 448  458           * file system, do so. This should only happen on a failed
 449      -         * writeop(i.e., we have acquired the write lock above).
      459 +         * writeop (i.e., we have acquired the write lock above).
 450  460           */
 451      -        if (access(IPADM_VOL_DB_FILE, F_OK) != 0) {
      461 +        if (access(tmpconfpath, F_OK) != 0) {
 452  462                  assert(writeop);
 453      -                err = ipmgmt_cpfile(IPADM_DB_FILE, IPADM_VOL_DB_FILE, B_TRUE);
      463 +                err = ipmgmt_cpfile(confpath, tmpconfpath, B_TRUE);
 454  464                  if (err != 0)
 455  465                          goto done;
 456  466                  (void) pthread_attr_init(&attr);
 457  467                  (void) pthread_attr_setdetachstate(&attr,
 458  468                      PTHREAD_CREATE_DETACHED);
 459  469                  err = pthread_create(&tid, &attr, ipmgmt_db_restore_thread,
 460  470                      NULL);
 461  471                  (void) pthread_attr_destroy(&attr);
 462  472                  if (err != 0) {
 463      -                        (void) unlink(IPADM_VOL_DB_FILE);
      473 +                        (void) unlink(tmpconfpath);
 464  474                          goto done;
 465  475                  }
 466  476                  ipmgmt_rdonly_root = B_TRUE;
 467  477          }
 468  478  
 469  479          /*
 470  480           * Read/write from the volatile copy.
 471  481           */
 472      -        err = ipadm_rw_db(db_walk_func, db_warg, IPADM_VOL_DB_FILE,
      482 +        err = ipadm_rw_db(db_walk_func, db_warg, tmpconfpath,
 473  483              mode, db_op);
 474  484  done:
 475  485          (void) pthread_rwlock_unlock(&ipmgmt_dbconf_lock);
 476  486          return (err);
 477  487  }
 478  488  
 479  489  /*
 480  490   * Used to add an entry towards the end of DB. It just returns B_TRUE for
 481  491   * every line of the DB. When we reach the end, ipadm_rw_db() adds the
 482  492   * line at the end.
↓ open down ↓ 747 lines elided ↑ open up ↑
1230 1240  
1231 1241  /*
1232 1242   * Adds or deletes aobjmap node information into a temporary cache file.
1233 1243   */
1234 1244  extern int
1235 1245  ipmgmt_persist_aobjmap(ipmgmt_aobjmap_t *nodep, ipadm_db_op_t op)
1236 1246  {
1237 1247          int                     err;
1238 1248          ipadm_dbwrite_cbarg_t   cb;
1239 1249          nvlist_t                *nvl = NULL;
     1250 +        char                    aobjpath[MAXPATHLEN];
1240 1251  
     1252 +        ipmgmt_path(IPADM_PATH_ADDROBJ_MAP_DB, aobjpath, sizeof (aobjpath));
     1253 +
1241 1254          if (op == IPADM_DB_WRITE) {
1242 1255                  if ((err = i_ipmgmt_node2nvl(&nvl, nodep)) != 0)
1243 1256                          return (err);
1244 1257                  cb.dbw_nvl = nvl;
1245 1258                  if (nodep->am_atype == IPADM_ADDR_IPV6_ADDRCONF)
1246 1259                          cb.dbw_flags = IPMGMT_ATYPE_V6ACONF;
1247 1260                  else
1248 1261                          cb.dbw_flags = 0;
1249 1262  
1250      -                err = ipadm_rw_db(ipmgmt_update_aobjmap, &cb,
1251      -                    ADDROBJ_MAPPING_DB_FILE, IPADM_FILE_MODE, IPADM_DB_WRITE);
     1263 +                err = ipadm_rw_db(ipmgmt_update_aobjmap, &cb, aobjpath,
     1264 +                    IPADM_FILE_MODE, IPADM_DB_WRITE);
1252 1265                  nvlist_free(nvl);
1253 1266          } else {
1254 1267                  assert(op == IPADM_DB_DELETE);
1255 1268  
1256      -                err = ipadm_rw_db(ipmgmt_delete_aobjmap, nodep,
1257      -                    ADDROBJ_MAPPING_DB_FILE, IPADM_FILE_MODE, IPADM_DB_DELETE);
     1269 +                err = ipadm_rw_db(ipmgmt_delete_aobjmap, nodep, aobjpath,
     1270 +                    IPADM_FILE_MODE, IPADM_DB_DELETE);
1258 1271          }
1259 1272          return (err);
1260 1273  }
1261 1274  
1262 1275  /*
1263 1276   * upgrades the ipadm data-store. It renames all the old private protocol
1264 1277   * property names which start with leading protocol names to begin with
1265 1278   * IPADM_PRIV_PROP_PREFIX.
1266 1279   */
1267 1280  /* ARGSUSED */
↓ open down ↓ 425 lines elided ↑ open up ↑
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX