summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDaniel Vetter <daniel.vetter@ffwll.ch>2011-09-19 23:16:58 +0200
committerDaniel Vetter <daniel.vetter@ffwll.ch>2011-09-19 23:16:58 +0200
commitbf89a1219dfe427bbbca0667c64c92c47eabec9f (patch)
treeb1dc5097fe34c5e970d946f0813ecdff3abd5196
parenta4418a09f8d4e2d103505f38b955eae91bd570dd (diff)
quick&dirty mappable/!mappable separationhole_stack-trick
not even compile-tested
-rw-r--r--drivers/gpu/drm/drm_mm.c18
-rw-r--r--include/drm/drm_mm.h1
2 files changed, 14 insertions, 5 deletions
diff --git a/drivers/gpu/drm/drm_mm.c b/drivers/gpu/drm/drm_mm.c
index 959186cbf328..c2ee964a0b8c 100644
--- a/drivers/gpu/drm/drm_mm.c
+++ b/drivers/gpu/drm/drm_mm.c
@@ -227,7 +227,7 @@ static void drm_mm_insert_helper_range(struct drm_mm_node *hole_node,
BUG_ON(node->start + node->size > end);
if (node->start + node->size < hole_end) {
- list_add(&node->hole_stack, &mm->hole_stack);
+ list_add_tail(&node->hole_stack, &mm->hole_stack);
node->hole_follows = 1;
} else {
node->hole_follows = 0;
@@ -301,9 +301,16 @@ void drm_mm_remove_node(struct drm_mm_node *node)
if (!prev_node->hole_follows) {
prev_node->hole_follows = 1;
- list_add(&prev_node->hole_stack, &mm->hole_stack);
- } else
- list_move(&prev_node->hole_stack, &mm->hole_stack);
+ if (mm->restricted_end > drm_mm_hole_node_start(prev_node))
+ list_add_tail(&prev_node->hole_stack, &mm->hole_stack);
+ else
+ list_add(&prev_node->hole_stack, &mm->hole_stack);
+ } else {
+ if (mm->restricted_end > drm_mm_hole_node_start(prev_node))
+ list_move_tail(&prev_node->hole_stack, &mm->hole_stack);
+ else
+ list_move(&prev_node->hole_stack, &mm->hole_stack);
+ }
list_del(&node->node_list);
node->allocated = 0;
@@ -398,11 +405,12 @@ struct drm_mm_node *drm_mm_search_free_in_range(const struct drm_mm *mm,
unsigned long best_size;
BUG_ON(mm->scanned_blocks);
+ mm->restricted_end = end;
best = NULL;
best_size = ~0UL;
- list_for_each_entry(entry, &mm->hole_stack, hole_stack) {
+ list_for_each_entry_reverse(entry, &mm->hole_stack, hole_stack) {
unsigned long adj_start = drm_mm_hole_node_start(entry) < start ?
start : drm_mm_hole_node_start(entry);
unsigned long adj_end = drm_mm_hole_node_end(entry) > end ?
diff --git a/include/drm/drm_mm.h b/include/drm/drm_mm.h
index 564b14aa7e16..5fd58c3ab611 100644
--- a/include/drm/drm_mm.h
+++ b/include/drm/drm_mm.h
@@ -72,6 +72,7 @@ struct drm_mm {
unsigned scanned_blocks;
unsigned long scan_start;
unsigned long scan_end;
+ unsigned long restricted_end;
struct drm_mm_node *prev_scanned_node;
};