Mercurial > mplayer.hg
comparison m_config.c @ 17471:63909962d3fc
Profiles support.
author | albeu |
---|---|
date | Tue, 24 Jan 2006 11:16:13 +0000 |
parents | bad703951cf9 |
children | 526abfe30498 |
comparison
equal
deleted
inserted
replaced
17470:21123e349463 | 17471:63909962d3fc |
---|---|
11 #include "m_config.h" | 11 #include "m_config.h" |
12 #include "m_option.h" | 12 #include "m_option.h" |
13 #include "mp_msg.h" | 13 #include "mp_msg.h" |
14 #include "help_mp.h" | 14 #include "help_mp.h" |
15 | 15 |
16 #define MAX_PROFILE_DEPTH 20 | |
17 | |
18 static int | |
19 parse_profile(m_option_t* opt,char *name, char *param, void* dst, int src); | |
20 | |
21 static void | |
22 set_profile(m_option_t *opt, void* dst, void* src); | |
23 | |
24 static int | |
25 show_profile(m_option_t *opt, char* name, char *param); | |
26 | |
27 static void | |
28 m_config_add_option(m_config_t *config, m_option_t *arg, char* prefix); | |
29 | |
16 m_config_t* | 30 m_config_t* |
17 m_config_new(void) { | 31 m_config_new(void) { |
18 m_config_t* config; | 32 m_config_t* config; |
33 static int inited = 0; | |
34 static m_option_type_t profile_opt_type; | |
35 static m_option_t ref_opts[] = { | |
36 { "profile", NULL, &profile_opt_type, CONF_NOSAVE, 0, 0, NULL }, | |
37 { "show-profile", show_profile, CONF_TYPE_PRINT_FUNC, CONF_NOCFG, 0, 0, NULL }, | |
38 { NULL, NULL, NULL, 0, 0, 0, NULL } | |
39 }; | |
40 int i; | |
19 | 41 |
20 config = (m_config_t*)calloc(1,sizeof(m_config_t)); | 42 config = (m_config_t*)calloc(1,sizeof(m_config_t)); |
21 config->lvl = 1; // 0 Is the defaults | 43 config->lvl = 1; // 0 Is the defaults |
44 if(!inited) { | |
45 inited = 1; | |
46 profile_opt_type = m_option_type_string_list; | |
47 profile_opt_type.parse = parse_profile; | |
48 profile_opt_type.set = set_profile; | |
49 } | |
50 config->self_opts = malloc(sizeof(ref_opts)); | |
51 memcpy(config->self_opts,ref_opts,sizeof(ref_opts)); | |
52 for(i = 0 ; config->self_opts[i].name ; i++) | |
53 config->self_opts[i].priv = config; | |
54 m_config_register_options(config,config->self_opts); | |
55 | |
22 return config; | 56 return config; |
23 } | 57 } |
24 | 58 |
25 void | 59 void |
26 m_config_free(m_config_t* config) { | 60 m_config_free(m_config_t* config) { |
27 m_config_option_t *i = config->opts, *ct; | 61 m_config_option_t *i = config->opts, *ct; |
28 m_config_save_slot_t *sl,*st; | 62 m_config_save_slot_t *sl,*st; |
63 m_profile_t *p,*pn; | |
64 int j; | |
29 | 65 |
30 #ifdef MP_DEBUG | 66 #ifdef MP_DEBUG |
31 assert(config != NULL); | 67 assert(config != NULL); |
32 #endif | 68 #endif |
33 | 69 |
46 free(i->name); | 82 free(i->name); |
47 ct = i->next; | 83 ct = i->next; |
48 free(i); | 84 free(i); |
49 i = ct; | 85 i = ct; |
50 } | 86 } |
87 for(p = config->profiles ; p ; p = pn) { | |
88 pn = p->next; | |
89 free(p->name); | |
90 if(p->desc) free(p->desc); | |
91 for(j = 0 ; j < p->num_opts ; j++) { | |
92 free(p->opts[2*j]); | |
93 if(p->opts[2*j+1]) free(p->opts[2*j+1]); | |
94 } | |
95 free(p->opts); | |
96 free(p); | |
97 } | |
98 free(config->self_opts); | |
51 free(config); | 99 free(config); |
52 } | 100 } |
53 | 101 |
54 void | 102 void |
55 m_config_push(m_config_t* config) { | 103 m_config_push(m_config_t* config) { |
379 opt->flags & CONF_NOCFG ? "No" : "Yes"); | 427 opt->flags & CONF_NOCFG ? "No" : "Yes"); |
380 count++; | 428 count++; |
381 } | 429 } |
382 mp_msg(MSGT_FIXME, MSGL_FIXME, MSGTR_TotalOptions,count); | 430 mp_msg(MSGT_FIXME, MSGL_FIXME, MSGTR_TotalOptions,count); |
383 } | 431 } |
432 | |
433 m_profile_t* | |
434 m_config_get_profile(m_config_t* config, char* name) { | |
435 m_profile_t* p; | |
436 for(p = config->profiles ; p ; p = p->next) | |
437 if(!strcmp(p->name,name)) return p; | |
438 return NULL; | |
439 } | |
440 | |
441 m_profile_t* | |
442 m_config_add_profile(m_config_t* config, char* name) { | |
443 m_profile_t* p = m_config_get_profile(config,name); | |
444 if(p) return p; | |
445 p = calloc(1,sizeof(m_profile_t)); | |
446 p->name = strdup(name); | |
447 p->next = config->profiles; | |
448 config->profiles = p; | |
449 return p; | |
450 } | |
451 | |
452 void | |
453 m_profile_set_desc(m_profile_t* p, char* desc) { | |
454 if(p->desc) free(p->desc); | |
455 p->desc = desc ? strdup(desc) : NULL; | |
456 } | |
457 | |
458 int | |
459 m_config_set_profile_option(m_config_t* config, m_profile_t* p, | |
460 char* name, char* val) { | |
461 int i = m_config_check_option(config,name,val); | |
462 if(i < 0) return i; | |
463 if(p->opts) p->opts = realloc(p->opts,2*(p->num_opts+2)*sizeof(char*)); | |
464 else p->opts = malloc(2*(p->num_opts+2)*sizeof(char*)); | |
465 p->opts[p->num_opts*2] = strdup(name); | |
466 p->opts[p->num_opts*2+1] = val ? strdup(val) : NULL; | |
467 p->num_opts++; | |
468 p->opts[p->num_opts*2] = p->opts[p->num_opts*2+1] = NULL; | |
469 } | |
470 | |
471 static void | |
472 m_config_set_profile(m_config_t* config, m_profile_t* p) { | |
473 int i; | |
474 if(config->profile_depth > MAX_PROFILE_DEPTH) { | |
475 mp_msg(MSGT_CFGPARSER, MSGL_WARN, "WARNING: Too deep profile inclusion\n"); | |
476 return; | |
477 } | |
478 config->profile_depth++; | |
479 for(i = 0 ; i < p->num_opts ; i++) | |
480 m_config_set_option(config,p->opts[2*i],p->opts[2*i+1]); | |
481 config->profile_depth--; | |
482 } | |
483 | |
484 static int | |
485 parse_profile(m_option_t* opt,char *name, char *param, void* dst, int src) { | |
486 m_config_t* config = opt->priv; | |
487 char** list = NULL; | |
488 int i,r; | |
489 if(param && !strcmp(param,"help")) { | |
490 m_profile_t* p; | |
491 if(!config->profiles) { | |
492 mp_msg(MSGT_FIXME, MSGL_FIXME, "No profile have been defined.\n"); | |
493 return M_OPT_EXIT-1; | |
494 } | |
495 mp_msg(MSGT_FIXME, MSGL_FIXME, "Available profiles:\n"); | |
496 for(p = config->profiles ; p ; p = p->next) | |
497 mp_msg(MSGT_FIXME, MSGL_FIXME, "\t%s\t%s\n",p->name, | |
498 p->desc ? p->desc : ""); | |
499 mp_msg(MSGT_FIXME, MSGL_FIXME, "\n"); | |
500 return M_OPT_EXIT-1; | |
501 } | |
502 | |
503 r = m_option_type_string_list.parse(opt,name,param,&list,src); | |
504 if(r < 0) return r; | |
505 if(!list || !list[0]) return M_OPT_INVALID; | |
506 for(i = 0 ; list[i] ; i++) | |
507 if(!m_config_get_profile(config,list[i])) { | |
508 mp_msg(MSGT_CFGPARSER, MSGL_WARN, "Unknown profile '%s'.\n", | |
509 list[i]); | |
510 r = M_OPT_INVALID; | |
511 } | |
512 if(dst) | |
513 m_option_copy(opt,dst,&list); | |
514 else | |
515 m_option_free(opt,&list); | |
516 return r; | |
517 } | |
518 | |
519 static void | |
520 set_profile(m_option_t *opt, void* dst, void* src) { | |
521 m_config_t* config = opt->priv; | |
522 m_profile_t* p; | |
523 char** list = NULL; | |
524 int i; | |
525 if(!src || !*(char***)src) return; | |
526 m_option_copy(opt,&list,src); | |
527 for(i = 0 ; list[i] ; i++) { | |
528 p = m_config_get_profile(config,list[i]); | |
529 if(!p) continue; | |
530 m_config_set_profile(config,p); | |
531 } | |
532 m_option_free(opt,&list); | |
533 } | |
534 | |
535 static int | |
536 show_profile(m_option_t *opt, char* name, char *param) { | |
537 m_config_t* config = opt->priv; | |
538 m_profile_t* p; | |
539 int i,j; | |
540 if(!param) return M_OPT_MISSING_PARAM; | |
541 if(!(p = m_config_get_profile(config,param))) { | |
542 mp_msg(MSGT_CFGPARSER, MSGL_ERR, "Unknown profile '%s'\n",param); | |
543 return M_OPT_EXIT-1; | |
544 } | |
545 if(!config->profile_depth) | |
546 mp_msg(MSGT_CFGPARSER, MSGL_INFO, "Profile %s: %s\n",param, | |
547 p->desc ? p->desc : ""); | |
548 config->profile_depth++; | |
549 for(i = 0 ; i < p->num_opts ; i++) { | |
550 char spc[config->profile_depth+1]; | |
551 for(j = 0 ; j < config->profile_depth ; j++) | |
552 spc[j] = ' '; | |
553 spc[config->profile_depth] = '\0'; | |
554 | |
555 mp_msg(MSGT_CFGPARSER, MSGL_INFO, "%s%s=%s\n", spc, | |
556 p->opts[2*i], p->opts[2*i+1]); | |
557 | |
558 | |
559 if(config->profile_depth < MAX_PROFILE_DEPTH && | |
560 !strcmp(p->opts[2*i],"profile")) { | |
561 char* e,*list = p->opts[2*i+1]; | |
562 while((e = strchr(list,','))) { | |
563 int l = e-list; | |
564 char tmp[l+1]; | |
565 if(!l) continue; | |
566 memcpy(tmp,list,l); | |
567 tmp[l] = '\0'; | |
568 show_profile(opt,name,tmp); | |
569 list = e+1; | |
570 } | |
571 if(list[0] != '\0') | |
572 show_profile(opt,name,list); | |
573 } | |
574 } | |
575 config->profile_depth--; | |
576 if(!config->profile_depth) mp_msg(MSGT_CFGPARSER, MSGL_INFO, "\n"); | |
577 return M_OPT_EXIT-1; | |
578 } |