summaryrefslogtreecommitdiff
path: root/sql/item.cc
diff options
context:
space:
mode:
Diffstat (limited to 'sql/item.cc')
-rw-r--r--sql/item.cc27
1 files changed, 27 insertions, 0 deletions
diff --git a/sql/item.cc b/sql/item.cc
index ea797679957..f317759553b 100644
--- a/sql/item.cc
+++ b/sql/item.cc
@@ -42,6 +42,20 @@ Item::Item()
decimals=0; max_length=0;
next=current_thd->free_list; // Put in free list
current_thd->free_list=this;
+ loop_id= 0;
+}
+
+bool Item::check_loop(uint id)
+{
+ DBUG_ENTER("Item::check_loop");
+ DBUG_PRINT("info", ("id %u, name %s", id, name));
+ if (loop_id == id)
+ {
+ DBUG_PRINT("info", ("id match"));
+ DBUG_RETURN(1);
+ }
+ loop_id= id;
+ DBUG_RETURN(0);
}
void Item::set_name(const char *str,uint length)
@@ -862,6 +876,11 @@ bool Item_ref::fix_fields(THD *thd,TABLE_LIST *tables, Item **reference)
{
depended_from= last;
thd->lex.current_select->mark_as_dependent(last);
+ if (check_loop(thd->check_loops_counter++))
+ {
+ my_message(ER_CYCLIC_REFERENCE, ER(ER_CYCLIC_REFERENCE), MYF(0));
+ return 1;
+ }
}
}
else if (!ref)
@@ -873,6 +892,14 @@ bool Item_ref::fix_fields(THD *thd,TABLE_LIST *tables, Item **reference)
return 0;
}
+bool Item_ref::check_loop(uint id)
+{
+ DBUG_ENTER("Item_ref::check_loop");
+ if (Item_ident::check_loop(id))
+ DBUG_RETURN(1);
+ DBUG_RETURN((*ref)->check_loop(id));
+}
+
/*
** If item is a const function, calculate it and return a const item
** The original item is freed if not returned