(hopefully) Fix FS#12639 and other skin related buflib corruption issues.
Kudos to funman for figuring out the problem - skin_find_item() rather stupidly uses the global skin_buffer variable in skin_parser.c which is fine in the parser EXCEPT it gets changed in skin_render when the sbs is being redrawn while another skin is loading, so fix this by makeing skin_find_item() use a local data pointer so a skin_render() during parsing won't break anything. Change-Id: I80e1c0efe569c18225e5772159c18ebb21e07332
This commit is contained in:
parent
027ebaf463
commit
7909bf039f
2 changed files with 18 additions and 31 deletions
|
@ -80,11 +80,6 @@
|
|||
#define WPS_ERROR_INVALID_PARAM -1
|
||||
|
||||
static char* skin_buffer = NULL;
|
||||
void skinparser_set_buffer(char* pointer)
|
||||
{
|
||||
skin_buffer = pointer;
|
||||
}
|
||||
|
||||
#if (LCD_DEPTH > 1) || (defined(HAVE_REMOTE_LCD) && (LCD_REMOTE_DEPTH > 1))
|
||||
static char *backdrop_filename;
|
||||
#endif
|
||||
|
@ -158,7 +153,6 @@ void *skin_find_item(const char *label, enum skin_find_what what,
|
|||
struct wps_data *data)
|
||||
{
|
||||
const char *itemlabel = NULL;
|
||||
char *old_skin_buffer = skin_buffer;
|
||||
char *databuf = get_skin_buffer(data);
|
||||
union {
|
||||
struct skin_token_list *linkedlist;
|
||||
|
@ -166,28 +160,28 @@ void *skin_find_item(const char *label, enum skin_find_what what,
|
|||
} list = {NULL};
|
||||
bool isvplist = false;
|
||||
void *ret = NULL;
|
||||
if (databuf && databuf != skin_buffer)
|
||||
skin_buffer = get_skin_buffer(data);
|
||||
if (!databuf)
|
||||
databuf = skin_buffer;
|
||||
switch (what)
|
||||
{
|
||||
case SKIN_FIND_UIVP:
|
||||
case SKIN_FIND_VP:
|
||||
list.vplist = SKINOFFSETTOPTR(skin_buffer, data->tree);
|
||||
list.vplist = SKINOFFSETTOPTR(databuf, data->tree);
|
||||
isvplist = true;
|
||||
break;
|
||||
#ifdef HAVE_LCD_BITMAP
|
||||
case SKIN_FIND_IMAGE:
|
||||
list.linkedlist = SKINOFFSETTOPTR(skin_buffer, data->images);
|
||||
list.linkedlist = SKINOFFSETTOPTR(databuf, data->images);
|
||||
break;
|
||||
#endif
|
||||
#ifdef HAVE_TOUCHSCREEN
|
||||
case SKIN_FIND_TOUCHREGION:
|
||||
list.linkedlist = SKINOFFSETTOPTR(skin_buffer, data->touchregions);
|
||||
list.linkedlist = SKINOFFSETTOPTR(databuf, data->touchregions);
|
||||
break;
|
||||
#endif
|
||||
#ifdef HAVE_SKIN_VARIABLES
|
||||
case SKIN_VARIABLE:
|
||||
list.linkedlist = SKINOFFSETTOPTR(skin_buffer, data->skinvars);
|
||||
list.linkedlist = SKINOFFSETTOPTR(databuf, data->skinvars);
|
||||
break;
|
||||
#endif
|
||||
}
|
||||
|
@ -198,54 +192,50 @@ void *skin_find_item(const char *label, enum skin_find_what what,
|
|||
#ifdef HAVE_LCD_BITMAP
|
||||
struct wps_token *token = NULL;
|
||||
if (!isvplist)
|
||||
token = SKINOFFSETTOPTR(skin_buffer, list.linkedlist->token);
|
||||
token = SKINOFFSETTOPTR(databuf, list.linkedlist->token);
|
||||
#endif
|
||||
switch (what)
|
||||
{
|
||||
case SKIN_FIND_UIVP:
|
||||
case SKIN_FIND_VP:
|
||||
ret = SKINOFFSETTOPTR(skin_buffer, list.vplist->data);
|
||||
ret = SKINOFFSETTOPTR(databuf, list.vplist->data);
|
||||
if (((struct skin_viewport *)ret)->label == VP_DEFAULT_LABEL)
|
||||
itemlabel = VP_DEFAULT_LABEL_STRING;
|
||||
else
|
||||
itemlabel = SKINOFFSETTOPTR(skin_buffer, ((struct skin_viewport *)ret)->label);
|
||||
itemlabel = SKINOFFSETTOPTR(databuf, ((struct skin_viewport *)ret)->label);
|
||||
skip = !(((struct skin_viewport *)ret)->is_infovp ==
|
||||
(what==SKIN_FIND_UIVP));
|
||||
break;
|
||||
#ifdef HAVE_LCD_BITMAP
|
||||
case SKIN_FIND_IMAGE:
|
||||
ret = SKINOFFSETTOPTR(skin_buffer, token->value.data);
|
||||
itemlabel = SKINOFFSETTOPTR(skin_buffer, ((struct gui_img *)ret)->label);
|
||||
ret = SKINOFFSETTOPTR(databuf, token->value.data);
|
||||
itemlabel = SKINOFFSETTOPTR(databuf, ((struct gui_img *)ret)->label);
|
||||
break;
|
||||
#endif
|
||||
#ifdef HAVE_TOUCHSCREEN
|
||||
case SKIN_FIND_TOUCHREGION:
|
||||
ret = SKINOFFSETTOPTR(skin_buffer, token->value.data);
|
||||
itemlabel = SKINOFFSETTOPTR(skin_buffer, ((struct touchregion *)ret)->label);
|
||||
ret = SKINOFFSETTOPTR(databuf, token->value.data);
|
||||
itemlabel = SKINOFFSETTOPTR(databuf, ((struct touchregion *)ret)->label);
|
||||
break;
|
||||
#endif
|
||||
#ifdef HAVE_SKIN_VARIABLES
|
||||
case SKIN_VARIABLE:
|
||||
ret = SKINOFFSETTOPTR(skin_buffer, token->value.data);
|
||||
itemlabel = SKINOFFSETTOPTR(skin_buffer, ((struct skin_var *)ret)->label);
|
||||
ret = SKINOFFSETTOPTR(databuf, token->value.data);
|
||||
itemlabel = SKINOFFSETTOPTR(databuf, ((struct skin_var *)ret)->label);
|
||||
break;
|
||||
#endif
|
||||
|
||||
}
|
||||
if (!skip && itemlabel && !strcmp(itemlabel, label))
|
||||
{
|
||||
if (old_skin_buffer != skin_buffer)
|
||||
skin_buffer = old_skin_buffer;
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (isvplist)
|
||||
list.vplist = SKINOFFSETTOPTR(skin_buffer, list.vplist->next);
|
||||
list.vplist = SKINOFFSETTOPTR(databuf, list.vplist->next);
|
||||
else
|
||||
list.linkedlist = SKINOFFSETTOPTR(skin_buffer, list.linkedlist->next);
|
||||
list.linkedlist = SKINOFFSETTOPTR(databuf, list.linkedlist->next);
|
||||
}
|
||||
if (old_skin_buffer != skin_buffer)
|
||||
skin_buffer = old_skin_buffer;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
@ -2330,5 +2320,6 @@ bool skin_data_load(enum screen_type screen, struct wps_data *wps_data,
|
|||
#else
|
||||
wps_data->wps_loaded = wps_data->tree >= 0;
|
||||
#endif
|
||||
skin_buffer = NULL;
|
||||
return true;
|
||||
}
|
||||
|
|
|
@ -84,8 +84,6 @@ static void skin_render_playlistviewer(struct playlistviewer* viewer,
|
|||
#endif
|
||||
|
||||
static char* skin_buffer;
|
||||
/* hack alert: fix skin_parser.c's skin_buffer pointer */
|
||||
void skinparser_set_buffer(char* pointer);
|
||||
|
||||
static inline struct skin_element*
|
||||
get_child(OFFSETTYPE(struct skin_element**) children, int child)
|
||||
|
@ -720,7 +718,6 @@ void skin_render_viewport(struct skin_element* viewport, struct gui_wps *gwps,
|
|||
struct align_pos * align = &info.align;
|
||||
bool needs_update;
|
||||
skin_buffer = get_skin_buffer(gwps->data);
|
||||
skinparser_set_buffer(skin_buffer);
|
||||
#ifdef HAVE_LCD_BITMAP
|
||||
/* Set images to not to be displayed */
|
||||
struct skin_token_list *imglist = SKINOFFSETTOPTR(skin_buffer, gwps->data->images);
|
||||
|
@ -805,7 +802,6 @@ void skin_render(struct gui_wps *gwps, unsigned refresh_mode)
|
|||
|
||||
int old_refresh_mode = refresh_mode;
|
||||
skin_buffer = get_skin_buffer(gwps->data);
|
||||
skinparser_set_buffer(skin_buffer);
|
||||
|
||||
#ifdef HAVE_LCD_CHARCELLS
|
||||
int i;
|
||||
|
|
Loading…
Reference in a new issue