Print this page
10703 smatch unreachable code checking needs reworking
Reviewed by: Toomas Soome <tsoome@me.com>
Reviewed by: Yuri Pankov <yuri.pankov@nexenta.com>


   4  * The contents of this file are subject to the terms of the
   5  * Common Development and Distribution License (the "License").
   6  * You may not use this file except in compliance with the License.
   7  *
   8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
   9  * or http://www.opensolaris.org/os/licensing.
  10  * See the License for the specific language governing permissions
  11  * and limitations under the License.
  12  *
  13  * When distributing Covered Code, include this CDDL HEADER in each
  14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15  * If applicable, add the following below this CDDL HEADER, with the
  16  * fields enclosed by brackets "[]" replaced with your own identifying
  17  * information: Portions Copyright [yyyy] [name of copyright owner]
  18  *
  19  * CDDL HEADER END
  20  */
  21 
  22 /*
  23  * Copyright (c) 2004, 2010, Oracle and/or its affiliates. All rights reserved.
  24  * Copyright 2018 Joyent, Inc.
  25  * Copyright (c) 2015, Syneto S.R.L. All rights reserved.
  26  * Copyright 2016 Toomas Soome <tsoome@me.com>
  27  * Copyright 2016 RackTop Systems.
  28  */
  29 
  30 /*
  31  * graph.c - master restarter graph engine
  32  *
  33  *   The graph engine keeps a dependency graph of all service instances on the
  34  *   system, as recorded in the repository.  It decides when services should
  35  *   be brought up or down based on service states and dependencies and sends
  36  *   commands to restarters to effect any changes.  It also executes
  37  *   administrator commands sent by svcadm via the repository.
  38  *
  39  *   The graph is stored in uu_list_t *dgraph and its vertices are
  40  *   graph_vertex_t's, each of which has a name and an integer id unique to
  41  *   its name (see dict.c).  A vertex's type attribute designates the type
  42  *   of object it represents: GVT_INST for service instances, GVT_SVC for
  43  *   service objects (since service instances may depend on another service,
  44  *   rather than service instance), GVT_FILE for files (which services may


5800                 gu->gu_wakeup = 0;
5801 
5802                 while ((e = graph_event_dequeue()) != NULL) {
5803                         MUTEX_LOCK(&e->gpe_lock);
5804                         MUTEX_UNLOCK(&gu->gu_lock);
5805 
5806                         while ((err = handle_graph_update_event(h, e)) ==
5807                             ECONNABORTED)
5808                                 libscf_handle_rebind(h);
5809 
5810                         if (err == 0)
5811                                 graph_event_release(e);
5812                         else
5813                                 graph_event_requeue(e);
5814 
5815                         MUTEX_LOCK(&gu->gu_lock);
5816                 }
5817 
5818                 MUTEX_UNLOCK(&gu->gu_lock);
5819         }
5820 
5821         /*
5822          * Unreachable for now -- there's currently no graceful cleanup
5823          * called on exit().
5824          */
5825         MUTEX_UNLOCK(&gu->gu_lock);
5826         scf_handle_destroy(h);
5827         return (NULL);
5828 }
5829 
5830 static void
5831 set_initial_milestone(scf_handle_t *h)
5832 {
5833         scf_instance_t *inst;
5834         char *fmri, *cfmri;
5835         size_t sz;
5836         int r;
5837 
5838         inst = safe_scf_instance_create(h);
5839         fmri = startd_alloc(max_scf_fmri_size);
5840 
5841         /*
5842          * If -m milestone= was specified, we want to set options_ovr/milestone
5843          * to it.  Otherwise we want to read what the milestone should be set
5844          * to.  Either way we need our inst.
5845          */
5846 get_self:
5847         if (scf_handle_decode_fmri(h, SCF_SERVICE_STARTD, NULL, NULL, inst,


6173          * Now that we've set st_load_complete we need to check can_come_up()
6174          * since if we booted to a milestone, then there won't be any more
6175          * state updates.
6176          */
6177         if (!go_single_user_mode && !go_to_level1 &&
6178             halting == -1) {
6179                 if (!sulogin_thread_running && !can_come_up()) {
6180                         (void) startd_thread_create(sulogin_thread, NULL);
6181                         sulogin_thread_running = B_TRUE;
6182                 }
6183         }
6184         MUTEX_UNLOCK(&dgraph_lock);
6185 
6186         (void) pthread_mutex_lock(&gu->gu_freeze_lock);
6187 
6188         /*CONSTCOND*/
6189         while (1) {
6190                 (void) pthread_cond_wait(&gu->gu_freeze_cv,
6191                     &gu->gu_freeze_lock);
6192         }
6193 
6194         /*
6195          * Unreachable for now -- there's currently no graceful cleanup
6196          * called on exit().
6197          */
6198         (void) pthread_mutex_unlock(&gu->gu_freeze_lock);
6199         scf_handle_destroy(h);
6200 
6201         return (NULL);
6202 }
6203 
6204 
6205 /*
6206  * int next_action()
6207  *   Given an array of timestamps 'a' with 'num' elements, find the
6208  *   lowest non-zero timestamp and return its index. If there are no
6209  *   non-zero elements, return -1.
6210  */
6211 static int
6212 next_action(hrtime_t *a, int num)
6213 {
6214         hrtime_t t = 0;
6215         int i = 0, smallest = -1;
6216 
6217         for (i = 0; i < num; i++) {
6218                 if (t == 0) {
6219                         t = a[i];
6220                         smallest = i;
6221                 } else if (a[i] != 0 && a[i] < t) {




   4  * The contents of this file are subject to the terms of the
   5  * Common Development and Distribution License (the "License").
   6  * You may not use this file except in compliance with the License.
   7  *
   8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
   9  * or http://www.opensolaris.org/os/licensing.
  10  * See the License for the specific language governing permissions
  11  * and limitations under the License.
  12  *
  13  * When distributing Covered Code, include this CDDL HEADER in each
  14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15  * If applicable, add the following below this CDDL HEADER, with the
  16  * fields enclosed by brackets "[]" replaced with your own identifying
  17  * information: Portions Copyright [yyyy] [name of copyright owner]
  18  *
  19  * CDDL HEADER END
  20  */
  21 
  22 /*
  23  * Copyright (c) 2004, 2010, Oracle and/or its affiliates. All rights reserved.
  24  * Copyright 2019 Joyent, Inc.
  25  * Copyright (c) 2015, Syneto S.R.L. All rights reserved.
  26  * Copyright 2016 Toomas Soome <tsoome@me.com>
  27  * Copyright 2016 RackTop Systems.
  28  */
  29 
  30 /*
  31  * graph.c - master restarter graph engine
  32  *
  33  *   The graph engine keeps a dependency graph of all service instances on the
  34  *   system, as recorded in the repository.  It decides when services should
  35  *   be brought up or down based on service states and dependencies and sends
  36  *   commands to restarters to effect any changes.  It also executes
  37  *   administrator commands sent by svcadm via the repository.
  38  *
  39  *   The graph is stored in uu_list_t *dgraph and its vertices are
  40  *   graph_vertex_t's, each of which has a name and an integer id unique to
  41  *   its name (see dict.c).  A vertex's type attribute designates the type
  42  *   of object it represents: GVT_INST for service instances, GVT_SVC for
  43  *   service objects (since service instances may depend on another service,
  44  *   rather than service instance), GVT_FILE for files (which services may


5800                 gu->gu_wakeup = 0;
5801 
5802                 while ((e = graph_event_dequeue()) != NULL) {
5803                         MUTEX_LOCK(&e->gpe_lock);
5804                         MUTEX_UNLOCK(&gu->gu_lock);
5805 
5806                         while ((err = handle_graph_update_event(h, e)) ==
5807                             ECONNABORTED)
5808                                 libscf_handle_rebind(h);
5809 
5810                         if (err == 0)
5811                                 graph_event_release(e);
5812                         else
5813                                 graph_event_requeue(e);
5814 
5815                         MUTEX_LOCK(&gu->gu_lock);
5816                 }
5817 
5818                 MUTEX_UNLOCK(&gu->gu_lock);
5819         }








5820 }
5821 
5822 static void
5823 set_initial_milestone(scf_handle_t *h)
5824 {
5825         scf_instance_t *inst;
5826         char *fmri, *cfmri;
5827         size_t sz;
5828         int r;
5829 
5830         inst = safe_scf_instance_create(h);
5831         fmri = startd_alloc(max_scf_fmri_size);
5832 
5833         /*
5834          * If -m milestone= was specified, we want to set options_ovr/milestone
5835          * to it.  Otherwise we want to read what the milestone should be set
5836          * to.  Either way we need our inst.
5837          */
5838 get_self:
5839         if (scf_handle_decode_fmri(h, SCF_SERVICE_STARTD, NULL, NULL, inst,


6165          * Now that we've set st_load_complete we need to check can_come_up()
6166          * since if we booted to a milestone, then there won't be any more
6167          * state updates.
6168          */
6169         if (!go_single_user_mode && !go_to_level1 &&
6170             halting == -1) {
6171                 if (!sulogin_thread_running && !can_come_up()) {
6172                         (void) startd_thread_create(sulogin_thread, NULL);
6173                         sulogin_thread_running = B_TRUE;
6174                 }
6175         }
6176         MUTEX_UNLOCK(&dgraph_lock);
6177 
6178         (void) pthread_mutex_lock(&gu->gu_freeze_lock);
6179 
6180         /*CONSTCOND*/
6181         while (1) {
6182                 (void) pthread_cond_wait(&gu->gu_freeze_cv,
6183                     &gu->gu_freeze_lock);
6184         }









6185 }
6186 
6187 
6188 /*
6189  * int next_action()
6190  *   Given an array of timestamps 'a' with 'num' elements, find the
6191  *   lowest non-zero timestamp and return its index. If there are no
6192  *   non-zero elements, return -1.
6193  */
6194 static int
6195 next_action(hrtime_t *a, int num)
6196 {
6197         hrtime_t t = 0;
6198         int i = 0, smallest = -1;
6199 
6200         for (i = 0; i < num; i++) {
6201                 if (t == 0) {
6202                         t = a[i];
6203                         smallest = i;
6204                 } else if (a[i] != 0 && a[i] < t) {