63
57
return (var_entry->val_int(&null_value));
61
Get variable by name and, if necessary, put the record of variable
62
use into the binary log.
64
When a user variable is invoked from an update query (INSERT, UPDATE etc),
65
stores this variable and its value in session->user_var_events, so that it can be
66
written to the binlog (will be written just before the query is written, see
69
@param session Current thread
70
@param name Variable name
71
@param[out] out_entry variable structure or NULL. The pointer is set
72
regardless of whether function succeeded or not.
77
1 Failed to put appropriate record into binary log
81
int get_var_with_binlog(Session *session, enum_sql_command sql_command,
82
LEX_STRING &name, user_var_entry **out_entry)
84
BINLOG_USER_VAR_EVENT *user_var_event;
85
user_var_entry *var_entry;
86
var_entry= get_variable(&session->user_vars, name, 0);
89
Any reference to user-defined variable which is done from stored
90
function or trigger affects their execution and the execution of the
91
calling statement. We must log all such variables even if they are
92
not involved in table-updating statements.
94
if (!(opt_bin_log && is_update_query(sql_command)))
96
*out_entry= var_entry;
103
If the variable does not exist, it's NULL, but we want to create it so
104
that it gets into the binlog (if it didn't, the slave could be
105
influenced by a variable of the same name previously set by another
107
We create it like if it had been explicitly set with SET before.
108
The 'new' mimics what sql_yacc.yy does when 'SET @a=10;'.
109
sql_set_variables() is what is called from 'case SQLCOM_SET_OPTION'
110
in dispatch_command()). Instead of building a one-element list to pass to
111
sql_set_variables(), we could instead manually call check() and update();
112
this would save memory and time; but calling sql_set_variables() makes
113
one unique place to maintain (sql_set_variables()).
115
Manipulation with lex is necessary since free_underlaid_joins
116
is going to release memory belonging to the main query.
119
List<set_var_base> tmp_var_list;
120
LEX *sav_lex= session->lex, lex_tmp;
121
session->lex= &lex_tmp;
123
tmp_var_list.push_back(new set_var_user(new Item_func_set_user_var(name,
125
/* Create the variable */
126
if (sql_set_variables(session, &tmp_var_list))
128
session->lex= sav_lex;
131
session->lex= sav_lex;
132
if (!(var_entry= get_variable(&session->user_vars, name, 0)))
135
else if (var_entry->used_query_id == session->query_id ||
136
mysql_bin_log.is_query_in_union(session, var_entry->used_query_id))
139
If this variable was already stored in user_var_events by this query
140
(because it's used in more than one place in the query), don't store
143
*out_entry= var_entry;
149
First we need to store value of var_entry, when the next situation
152
> insert into t1 values (@a), (@a:=@a+1), (@a:=@a+1);
153
We have to write to binlog value @a= 1.
155
We allocate the user_var_event on user_var_events_alloc pool, not on
156
the this-statement-execution pool because in SPs user_var_event objects
157
may need to be valid after current [SP] statement execution pool is
160
size= ALIGN_SIZE(sizeof(BINLOG_USER_VAR_EVENT)) + var_entry->length;
161
if (!(user_var_event= (BINLOG_USER_VAR_EVENT *)
162
alloc_root(session->user_var_events_alloc, size)))
165
user_var_event->value= (char*) user_var_event +
166
ALIGN_SIZE(sizeof(BINLOG_USER_VAR_EVENT));
167
user_var_event->user_var_event= var_entry;
168
user_var_event->type= var_entry->type;
169
user_var_event->charset_number= var_entry->collation.collation->number;
170
if (!var_entry->value)
173
user_var_event->length= 0;
174
user_var_event->value= 0;
178
user_var_event->length= var_entry->length;
179
memcpy(user_var_event->value, var_entry->value,
182
/* Mark that this variable has been used by this query */
183
var_entry->used_query_id= session->query_id;
184
if (insert_dynamic(&session->user_var_events, (unsigned char*) &user_var_event))
187
*out_entry= var_entry;
191
*out_entry= var_entry;
66
195
void Item_func_get_user_var::fix_length_and_dec()
197
Session *session=current_session;
69
200
decimals=NOT_FIXED_DEC;
70
201
max_length=MAX_BLOB_WIDTH;
72
var_entry= session.getVariable(name, false);
203
error= get_var_with_binlog(session, session->lex->sql_command, name, &var_entry);
75
206
If the variable didn't exist it has been created as a STRING-type.