Changeset 5cb41d1b3661f82c7315a810af6e7b54298dafd6

Show
Ignore:
Timestamp:
11/24/09 03:10:57 (3 years ago)
Author:
Nedko Arnaudov <nedko@…>
Children:
4d061b7a395988015d68223c9fc0f17d9089dad7
Parents:
e5b356ebda47eb1f7bd963d5b216c953e807d406
git-committer:
Nedko Arnaudov <nedko@arnaudov.name> / 2009-11-24T03:10:57Z+0200
Message:

switch from event queue to environment state; run the studio cqueue

Location:
daemon
Files:
3 modified

Legend:

Unmodified
Added
Removed
  • daemon/studio.c

    rc9567a3 r5cb41d1  
    4646struct studio g_studio; 
    4747 
    48 #define EVENT_JACK_START   0 
    49 #define EVENT_JACK_STOP    1 
    50  
    51 struct event 
    52 { 
    53   struct list_head siblings; 
    54   unsigned int type; 
    55 }; 
    56  
    5748bool studio_name_generate(char ** name_ptr) 
    5849{ 
     
    124115bool studio_start(void) 
    125116{ 
    126   if (g_studio.jack_pending) 
    127   { 
    128     log_error("JACK is not in stable state"); 
    129     return false; 
    130   } 
    131  
    132   if (!g_studio.jack_running) 
    133   { 
    134     log_info("Starting JACK server."); 
    135  
    136     g_studio.jack_pending = true; 
    137     if (!jack_proxy_start_server()) 
    138     { 
    139       log_error("jack_proxy_start_server() failed."); 
    140       return false; 
    141     } 
    142   } 
    143  
    144   return true; 
    145 } 
    146  
    147 static bool studio_stop(bool clear, bool * clear_defered_ptr) 
    148 { 
    149   if (g_studio.jack_pending) 
    150   { 
    151     log_error("JACK is not in stable state"); 
    152     return false; 
    153   } 
    154  
    155   if (g_studio.jack_running) 
    156   { 
    157     log_info("Stopping JACK server..."); 
    158  
    159     g_studio.automatic = false;   /* even if it was automatic, it is not anymore because user knows about it */ 
    160  
    161     g_studio.jack_pending = true; 
    162  
    163     if (clear) 
    164     { 
    165       log_info("defer studio clear until jack stops"); 
    166       g_studio.clear_on_jack_stop = true; 
    167       *clear_defered_ptr = true; 
    168     } 
    169  
    170     if (!jack_proxy_stop_server()) 
    171     { 
    172       log_error("Stopping JACK server failed."); 
    173       g_studio.jack_pending = false; 
    174       return false; 
    175     } 
    176   } 
    177   else if (clear) 
    178   { 
    179     *clear_defered_ptr = false; 
    180   } 
    181  
    182   return true; 
    183 } 
    184  
    185 bool studio_clear(bool defer_if_started) 
    186 { 
    187   bool clear_defered; 
    188  
     117  if (ladish_environment_get(&g_studio.env_store, ladish_environment_jack_server_started)) 
     118  { 
     119    log_info("JACK server is already started"); 
     120    return true; 
     121  } 
     122 
     123  log_info("Starting JACK server."); 
     124 
     125  if (!jack_proxy_start_server()) 
     126  { 
     127    log_error("jack_proxy_start_server() failed."); 
     128    return false; 
     129  } 
     130 
     131  return true; 
     132} 
     133 
     134static bool studio_stop(void) 
     135{ 
     136  if (!ladish_environment_get(&g_studio.env_store, ladish_environment_jack_server_started)) 
     137  { 
     138    log_info("JACK server is already stopped"); 
     139    return true; 
     140  } 
     141 
     142  log_info("Stopping JACK server..."); 
     143 
     144  g_studio.automatic = false;   /* even if it was automatic, it is not anymore because user knows about it */ 
     145 
     146  if (!jack_proxy_stop_server()) 
     147  { 
     148    log_error("Stopping JACK server failed."); 
     149    return false; 
     150  } 
     151 
     152  return true; 
     153} 
     154 
     155bool studio_clear(void) 
     156{ 
    189157  log_info("studio_clear() called."); 
    190158 
    191   if (!studio_stop(defer_if_started, &clear_defered)) 
    192   { 
    193     return false; 
    194   } 
    195  
    196   if (defer_if_started && clear_defered) 
    197   { 
    198     return true; 
     159  if (!studio_stop()) 
     160  { 
     161    return false; 
    199162  } 
    200163 
     
    238201  { 
    239202    log_info("Unloading automatic studio."); 
    240     studio_clear(true); 
     203    studio_clear(); 
    241204    return; 
    242205  } 
     
    245208void on_event_jack_started(void) 
    246209{ 
    247   g_studio.jack_pending = false; 
    248   g_studio.jack_running = true; 
    249  
    250210  if (g_studio.dbus_object == NULL) 
    251211  { 
     
    296256{ 
    297257  emit_studio_stopped(); 
    298   g_studio.jack_pending = false; 
    299   g_studio.jack_running = false; 
    300  
    301   if (g_studio.clear_on_jack_stop) 
    302   { 
    303     g_studio.clear_on_jack_stop = false; 
    304     studio_clear(false); 
    305   } 
    306   else 
    307   { 
    308     studio_clear_if_automatic(); 
    309   } 
     258  studio_clear_if_automatic(); 
    310259 
    311260  if (g_studio.jack_dispatcher) 
     
    326275void studio_run(void) 
    327276{ 
    328   struct event * event_ptr; 
    329  
    330   while (!list_empty(&g_studio.event_queue)) 
    331   { 
    332     event_ptr = list_entry(g_studio.event_queue.next, struct event, siblings); 
    333     list_del(g_studio.event_queue.next); 
    334  
    335     switch (event_ptr->type) 
    336     { 
    337     case EVENT_JACK_START: 
     277  bool state; 
     278 
     279  ladish_cqueue_run(&g_studio.cmd_queue); 
     280 
     281  if (ladish_environment_consume_change(&g_studio.env_store, ladish_environment_jack_server_started, &state)) 
     282  { 
     283    if (state) 
     284    { 
    338285      on_event_jack_started(); 
    339       break; 
    340     case EVENT_JACK_STOP: 
     286    } 
     287    else 
     288    { 
    341289      on_event_jack_stopped(); 
    342       break; 
    343     } 
    344  
    345     free(event_ptr); 
    346   } 
     290    } 
     291  } 
     292 
     293  ladish_environment_ignore(&g_studio.env_store, ladish_environment_jack_server_present); 
     294  ladish_environment_assert_consumed(&g_studio.env_store); 
    347295} 
    348296 
    349297static void on_jack_server_started(void) 
    350298{ 
    351   struct event * event_ptr; 
    352  
    353299  log_info("JACK server start detected."); 
    354  
    355   event_ptr = malloc(sizeof(struct event)); 
    356   if (event_ptr == NULL) 
    357   { 
    358     log_error("malloc() failed to allocate struct event. Ignoring JACK start."); 
    359     return; 
    360   } 
    361  
    362   event_ptr->type = EVENT_JACK_START; 
    363   list_add_tail(&event_ptr->siblings, &g_studio.event_queue); 
     300  ladish_environment_set(&g_studio.env_store, ladish_environment_jack_server_started); 
    364301} 
    365302 
    366303static void on_jack_server_stopped(void) 
    367304{ 
    368   struct event * event_ptr; 
    369  
    370   log_info("JACK server stop detected."); 
    371  
    372   event_ptr = malloc(sizeof(struct event)); 
    373   if (event_ptr == NULL) 
    374   { 
    375     log_error("malloc() failed to allocate struct event. Ignoring JACK stop."); 
    376     return; 
    377   } 
    378  
    379   event_ptr->type = EVENT_JACK_STOP; 
    380   list_add_tail(&event_ptr->siblings, &g_studio.event_queue); 
     305  ladish_environment_reset(&g_studio.env_store, ladish_environment_jack_server_started); 
    381306} 
    382307 
     
    384309{ 
    385310  log_info("JACK controller appeared."); 
     311  ladish_environment_set(&g_studio.env_store, ladish_environment_jack_server_present); 
    386312} 
    387313 
     
    389315{ 
    390316  log_info("JACK controller disappeared."); 
     317  ladish_environment_reset(&g_studio.env_store, ladish_environment_jack_server_present); 
    391318} 
    392319 
     
    420347  INIT_LIST_HEAD(&g_studio.jack_params); 
    421348 
    422   INIT_LIST_HEAD(&g_studio.event_queue); 
    423  
    424349  g_studio.dbus_object = NULL; 
    425350  g_studio.name = NULL; 
    426351  g_studio.filename = NULL; 
    427   g_studio.jack_running = false; 
    428   g_studio.jack_pending = false; 
    429352 
    430353  if (!ladish_graph_create(&g_studio.jack_graph, NULL)) 
     
    441364 
    442365  ladish_cqueue_init(&g_studio.cmd_queue); 
     366  ladish_environment_init(&g_studio.env_store); 
    443367 
    444368  if (!jack_proxy_init( 
     
    459383  ladish_graph_destroy(g_studio.jack_graph, false); 
    460384free_studios_dir: 
    461   studio_clear(false); 
     385  studio_clear(); 
    462386  free(g_studios_dir); 
    463387fail: 
     
    471395  jack_proxy_uninit(); 
    472396 
    473   studio_clear(false); 
     397  studio_clear(); 
    474398 
    475399  ladish_cqueue_uninit(&g_studio.cmd_queue); 
     
    685609{ 
    686610  log_info("Unload studio request"); 
    687   studio_clear(true); 
     611  studio_clear(); 
    688612  method_return_new_void(call_ptr); 
    689613} 
     
    692616{ 
    693617  log_info("New studio request (%s)", studio_name); 
    694   if (!studio_clear(false)) 
     618  if (!studio_clear()) 
    695619  { 
    696620    lash_dbus_error(call_ptr, LASH_DBUS_ERROR_GENERIC, "Cannot create new studio when other studio is running."); 
     
    717641  { 
    718642    lash_dbus_error(call_ptr, LASH_DBUS_ERROR_GENERIC, "studio_publish() failed."); 
    719     studio_clear(false); 
     643    studio_clear(); 
    720644    return false; 
    721645  } 
     
    728652  log_info("Studio stop requested"); 
    729653 
    730   if (!studio_stop(false, NULL)) 
     654  if (!studio_stop()) 
    731655  { 
    732656      lash_dbus_error(call_ptr, LASH_DBUS_ERROR_GENERIC, "Failed to stop studio."); 
  • daemon/studio_internal.h

    r1b1d5bb r5cb41d1  
    3636#define JACK_CONF_MAX_ADDRESS_SIZE 1024 
    3737 
     38typedef int ladish_environment_id; 
     39 
     40typedef struct 
     41{ 
     42  uint64_t state; 
     43  uint64_t changed; 
     44} ladish_environment_store; 
     45 
     46#define ladish_environment_jack_server_present    ((ladish_environment_id)0) 
     47#define ladish_environment_jack_server_started    ((ladish_environment_id)1) 
     48 
     49static inline void ladish_environment_init(ladish_environment_store * store_ptr) 
     50{ 
     51  store_ptr->state = 0; 
     52  store_ptr->changed = 0; 
     53} 
     54 
     55static inline uint64_t ladish_environment_state(ladish_environment_id id) 
     56{ 
     57  ASSERT(sizeof(id) < 8); 
     58  return (uint64_t)1 << id; 
     59} 
     60 
     61static inline void ladish_environment_set(ladish_environment_store * store_ptr, ladish_environment_id id) 
     62{ 
     63  uint64_t state = ladish_environment_state(id); 
     64  store_ptr->state |= state; 
     65  store_ptr->changed |= state; 
     66} 
     67 
     68static inline void ladish_environment_reset(ladish_environment_store * store_ptr, ladish_environment_id id) 
     69{ 
     70  uint64_t state = ladish_environment_state(id); 
     71  store_ptr->state &= ~state; 
     72  store_ptr->changed |= state; 
     73} 
     74 
     75static inline bool ladish_environment_get(ladish_environment_store * store_ptr, ladish_environment_id id) 
     76{ 
     77  uint64_t state = ladish_environment_state(id); 
     78 
     79  return (store_ptr->state & state) == state; 
     80} 
     81 
     82static inline bool ladish_environment_consume_change(ladish_environment_store * store_ptr, ladish_environment_id id, bool * new_state) 
     83{ 
     84  uint64_t state = ladish_environment_state(id); 
     85 
     86  if ((store_ptr->changed & state) == 0) 
     87  { 
     88    return false; 
     89  } 
     90 
     91  *new_state = (store_ptr->state & state) == state; 
     92  store_ptr->changed &= ~state; 
     93  return true; 
     94} 
     95 
     96static inline void ladish_environment_ignore(ladish_environment_store * store_ptr, ladish_environment_id id) 
     97{ 
     98  uint64_t state = ladish_environment_state(id); 
     99 
     100  if ((store_ptr->changed & state) != 0) 
     101  { 
     102    store_ptr->changed &= ~state; 
     103  } 
     104} 
     105 
     106#define ladish_environment_assert_consumed(store_ptr) ASSERT((store_ptr)->changed == 0) 
     107 
    38108struct studio 
    39109{ 
     
    52122  bool modified:1;              /* Studio needs saving */ 
    53123  bool jack_conf_valid:1;       /* JACK server configuration obtained successfully */ 
    54   bool jack_running:1;          /* JACK server is running */ 
    55   bool jack_pending:1;          /* JACK server start/stop is pending */ 
    56   bool clear_on_jack_stop:1;    /* clear studio when JACK is stopped */ 
    57124 
    58125  struct list_head jack_conf;   /* root of the conf tree */ 
     
    62129 
    63130  struct ladish_cqueue cmd_queue; 
    64   struct list_head event_queue; 
     131  ladish_environment_store env_store; 
    65132 
    66133  char * name; 
     
    106173bool studio_fetch_jack_settings(void); 
    107174bool studio_compose_filename(const char * name, char ** filename_ptr_ptr, char ** backup_filename_ptr_ptr); 
    108 bool studio_clear(bool defer_if_started); 
     175bool studio_clear(void); 
    109176bool studio_publish(void); 
    110177bool studio_start(void); 
  • daemon/studio_load.c

    r689ef7c r5cb41d1  
    667667  } 
    668668 
    669   studio_clear(false); 
     669  studio_clear(); 
    670670 
    671671  g_studio.name = strdup(studio_name); 
     
    743743    XML_ParserFree(parser); 
    744744    close(fd); 
    745     studio_clear(false); 
     745    studio_clear(); 
    746746    return false; 
    747747  } 
     
    753753  { 
    754754    /* if we have initiated the fail, dbus error is already set to better message */ 
    755     studio_clear(false); 
     755    studio_clear(); 
    756756    return false; 
    757757  } 
     
    766766  { 
    767767    lash_dbus_error(call_ptr, LASH_DBUS_ERROR_GENERIC, "studio_publish() failed."); 
    768     studio_clear(false); 
     768    studio_clear(); 
    769769    return false; 
    770770  } 
     
    773773  { 
    774774      lash_dbus_error(call_ptr, LASH_DBUS_ERROR_GENERIC, "Failed to start JACK server."); 
    775       studio_clear(false); 
     775      studio_clear(); 
    776776      return false; 
    777777  }