7 #include "pnd_logger.h"
9 #include "pnd_container.h"
10 #include "pnd_discovery.h"
11 #include "../lib/pnd_pathiter.h"
17 mm_category_t g_categories [ MAX_CATS ];
18 unsigned char g_categorycount = 0;
20 mm_catmap_t g_catmaps [ MAX_CATS ];
21 unsigned char g_catmapcount = 0;
23 extern pnd_conf_handle g_conf;
25 unsigned char category_push ( char *catname, pnd_disco_t *app ) {
28 // check category list; if found, append app to the end of it.
29 // if not found, add it to the category list and plop the app in there.
30 // app's are just app-refs, which contain links to the disco-t list -- thus removal is only in one place, and
31 // an app can be in multiple categories if we like..
34 // find or create category
37 if ( ( c = category_query ( catname ) ) ) {
38 // category was found..
40 // category wasn't found..
41 pnd_log ( PND_LOG_DEFAULT, "New category '%s'\n", catname );
42 g_categories [ g_categorycount ].catname = strdup ( catname );
43 g_categories [ g_categorycount ].refs = NULL;
44 c = &(g_categories [ g_categorycount ]);
49 return ( 1 ); // create cat, but skip app
52 // alloc and populate appref
54 mm_appref_t *ar = malloc ( sizeof(mm_appref_t) );
59 bzero ( ar, sizeof(mm_appref_t) );
63 // plug it into category
64 // and sort it on insert!
66 ar -> next = c -> refs;
69 // if no refs at all, or new guy has no title, just stick it in at head
70 if ( c -> refs && ar -> ref -> title_en ) {
71 mm_appref_t *iter = c -> refs;
72 mm_appref_t *last = NULL;
76 if ( iter -> ref -> title_en ) {
77 if ( strcmp ( ar -> ref -> title_en, iter -> ref -> title_en ) < 0 ) {
78 // new guy is smaller than the current guy!
82 // since new guy must have a name by here, we're bigger than any guy who does not have a name
91 // smaller than the current guy, so stitch in
96 ar -> next = c -> refs;
100 // we're the biggest, just append to last
105 ar -> next = c -> refs;
114 mm_category_t *category_query ( char *catname ) {
117 for ( i = 0; i < g_categorycount; i++ ) {
119 if ( strcasecmp ( g_categories [ i ].catname, catname ) == 0 ) {
120 return ( &(g_categories [ i ]) );
128 void category_dump ( void ) {
131 // WHY AREN'T I SORTING ON INSERT?
134 for ( i = 0; i < g_categorycount; i++ ) {
135 pnd_log ( PND_LOG_DEFAULT, "Category %u: '%s' * %u\n", i, g_categories [ i ].catname, g_categories [ i ].refcount );
136 mm_appref_t *ar = g_categories [ i ].refs;
139 pnd_log ( PND_LOG_DEFAULT, " Appref %s\n", IFNULL(ar -> ref -> title_en,"No Name") );
148 void category_freeall ( void ) {
150 mm_appref_t *iter, *next;
152 for ( i = 0; i < g_categorycount; i++ ) {
154 iter = g_categories [ i ].refs;
162 g_categories [ i ].refs = NULL;
171 unsigned char category_map_setup ( void ) {
173 char *searchpath = pnd_box_get_head ( g_conf );
175 if ( ! searchpath ) {
179 // look through conf for useful keys
180 while ( searchpath ) {
181 char *k = pnd_box_get_key ( searchpath );
183 // does this key look like a category mapping key?
184 if ( strncasecmp ( k, "categories.@", 12 ) == 0 ) {
187 // iterate across 'words' in v, assigning catmaps to them
190 //pnd_log ( pndn_debug, "target(%s) from(%s)\n", k, buffer );
192 category_push ( k, NULL );
193 g_catmaps [ g_catmapcount ].target = category_query ( k );
194 g_catmaps [ g_catmapcount ].from = strdup ( buffer );
200 } // if key looks like catmap
202 searchpath = pnd_box_get_next ( searchpath );
203 } // while each conf key
208 mm_category_t *category_map_query ( char *cat ) {
211 for ( i = 0; i < g_catmapcount; i++ ) {
212 if ( strcasecmp ( g_catmaps [ i ].from, cat ) == 0 ) {
213 return ( g_catmaps [ i ].target );
220 unsigned char category_meta_push ( char *catname, pnd_disco_t *app ) {
223 // do we honour cat mapping at all?
224 if ( pnd_conf_get_as_int_d ( g_conf, "categories.map_on", 0 ) ) {
226 // is this guy mapped?
227 cat = category_map_query ( catname );
230 return ( category_push ( cat -> catname, app ) );
233 // not mapped.. but default?
234 if ( pnd_conf_get_as_int_d ( g_conf, "categories.map_default_on", 0 ) ) {
235 char *def = pnd_conf_get_as_char ( g_conf, "categories.map_default_cat" );
237 return ( category_push ( def, app ) );
241 } // cat map is desired?
243 // not default, just do it
244 return ( category_push ( catname, app ) );