[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-changelog] [xen-unstable] x86: Fix clip_to_limit().
# HG changeset patch # User Keir Fraser <keir.fraser@xxxxxxxxxx> # Date 1257799420 0 # Node ID a84b90980632d97ad19998165d7b130be04b77af # Parent ad0419c835c806e470802065fe44a59fbd725cdf x86: Fix clip_to_limit(). There are issues in updating the e820 map in the middle of a loop that iterates over it. For example, after memmove(&e820.map[i], &e820.map[i+1], ...), the original e820.map[i+1] become current e820.map[i] but the next loop count is i+1, so the original e820.map[i+1] will be skipped. Fix and clarify the code by making a double loop. Original bug discovery and fix by Xiao Guangrong <ericxiao.gr@xxxxxxxxx> Signed-off-by: Keir Fraser <keir.fraser@xxxxxxxxxx> --- xen/arch/x86/e820.c | 37 +++++++++++++++++++++++++------------ 1 files changed, 25 insertions(+), 12 deletions(-) diff -r ad0419c835c8 -r a84b90980632 xen/arch/x86/e820.c --- a/xen/arch/x86/e820.c Mon Nov 09 20:06:48 2009 +0000 +++ b/xen/arch/x86/e820.c Mon Nov 09 20:43:40 2009 +0000 @@ -367,19 +367,32 @@ static void __init clip_to_limit(uint64_ char _warnmsg[160]; uint64_t old_limit = 0; - for ( i = 0; i < e820.nr_map; i++ ) - { - if ( (e820.map[i].type != E820_RAM) || - ((e820.map[i].addr + e820.map[i].size) <= limit) ) + for ( ; ; ) + { + /* Find a RAM region needing clipping. */ + for ( i = 0; i < e820.nr_map; i++ ) + if ( (e820.map[i].type == E820_RAM) && + ((e820.map[i].addr + e820.map[i].size) > limit) ) + break; + + /* If none found, we are done. */ + if ( i == e820.nr_map ) + break; + + old_limit = max_t( + uint64_t, old_limit, e820.map[i].addr + e820.map[i].size); + + /* We try to convert clipped RAM areas to E820_UNUSABLE. */ + if ( e820_change_range_type(&e820, max(e820.map[i].addr, limit), + e820.map[i].addr + e820.map[i].size, + E820_RAM, E820_UNUSABLE) ) continue; - old_limit = e820.map[i].addr + e820.map[i].size; - if ( e820_change_range_type(&e820, max(e820.map[i].addr, limit), - old_limit, E820_RAM, E820_UNUSABLE) ) - { - /* Start again now e820 map must have changed. */ - i = 0; - } - else if ( e820.map[i].addr < limit ) + + /* + * If the type change fails (e.g., not space in table) then we clip or + * delete the region as appropriate. + */ + if ( e820.map[i].addr < limit ) { e820.map[i].size = limit - e820.map[i].addr; } _______________________________________________ Xen-changelog mailing list Xen-changelog@xxxxxxxxxxxxxxxxxxx http://lists.xensource.com/xen-changelog
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |