CUBRID Engine  latest
replication.c
Go to the documentation of this file.
1 /*
2  * Copyright 2008 Search Solution Corporation
3  * Copyright 2016 CUBRID Corporation
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at
8  *
9  * http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  *
17  */
18 
19 /*
20  * replication.c -
21  */
22 
23 #ident "$Id$"
24 
25 #include "replication.h"
26 
27 #include "dbtype.h"
28 #include "heap_file.h"
29 #include "log_lsa.hpp"
30 #include "object_primitive.h"
31 #include "object_representation.h"
32 #include "transform.h"
33 
34 #include <assert.h>
35 #include <stdio.h>
36 
37 /*
38  * EXTERN TO ALL SERVER RECOVERY FUNCTION CODED SOMEWHERE ELSE
39  */
40 
41 #define REPL_LOG_IS_NOT_EXISTS(tran_index) \
42  (log_Gl.trantable.all_tdes[(tran_index)]->num_repl_records == 0)
43 #define REPL_LOG_IS_FULL(tran_index) \
44  (log_Gl.trantable.all_tdes[(tran_index)]->num_repl_records \
45  == log_Gl.trantable.all_tdes[(tran_index)]->cur_repl_record+1)
46 
47 static const int REPL_LOG_INFO_ALLOC_SIZE = 100;
48 
49 #if defined(SERVER_MODE) || defined(SA_MODE)
50 static int repl_log_info_alloc (LOG_TDES * tdes, int arr_size, bool need_realloc);
51 #endif /* SERVER_MODE || SA_MODE */
52 
53 #if defined(SERVER_MODE) || defined(SA_MODE)
54 
55 /*
56  * repl_data_insert_log_dump - dump the "DATA INSERT" replication log
57  *
58  * return:
59  *
60  * length(in): length of the data
61  * data(in): log data
62  *
63  * NOTE:
64  */
65 void
66 repl_data_insert_log_dump (FILE * fp, int length, void *data)
67 {
68  char *class_name;
69  DB_VALUE key;
70  char *ptr;
71 
72  ptr = or_unpack_string_nocopy ((char *) data, &class_name);
73  ptr = or_unpack_mem_value (ptr, &key);
74  fprintf (fp, " class_name: %s\n", class_name);
75  fprintf (fp, " pk_value: ");
76  db_value_print (&key);
77  pr_clear_value (&key);
78  fprintf (fp, "\n");
79  fflush (fp);
80 }
81 
82 #if defined (ENABLE_UNUSED_FUNCTION)
83 /*
84  * repl_data_udpate_log_dump - dump the "DATA UPDATE" replication log
85  *
86  * return:
87  *
88  * length(in): length of the data
89  * data(in): log data
90  *
91  * NOTE:
92  */
93 void
94 repl_data_udpate_log_dump (FILE * fp, int length, void *data)
95 {
96  /* currently same logic as insert case, but I can't gaurantee it's true after this... */
97  repl_data_insert_log_dump (fp, length, data);
98 }
99 
100 /*
101  * repl_data_delete_log_dump - dump the "DATA DELETE" replication log
102  *
103  * return:
104  *
105  * length(in): length of the data
106  * data(in): log data
107  *
108  * NOTE:
109  */
110 void
111 repl_data_delete_log_dump (FILE * fp, int length, void *data)
112 {
113  /* currently same logic as insert case, but I can't gaurantee it's true after this... */
114  repl_data_insert_log_dump (fp, length, data);
115 }
116 
117 #endif
118 
119 /*
120  * repl_schema_log_dump -
121  *
122  * return:
123  *
124  * length(in):
125  * data(in):
126  *
127  * NOTE:
128  */
129 void
130 repl_schema_log_dump (FILE * fp, int length, void *data)
131 {
132  int type;
133  char *class_name, *ddl;
134  char *ptr;
135 
136  ptr = or_unpack_int ((char *) data, &type);
137  ptr = or_unpack_string_nocopy (ptr, &class_name);
138  ptr = or_unpack_string_nocopy (ptr, &ddl);
139  fprintf (fp, " type: %d\n", type);
140  fprintf (fp, " class_name: %s\n", class_name);
141  fprintf (fp, " DDL: %s\n", ddl);
142  fflush (fp);
143 }
144 
145 /*
146  * repl_log_info_alloc - log info area allocation
147  *
148  * return: Error Code
149  *
150  * tdes(in): transaction descriptor
151  * arr_size(in): array size to be allocated
152  * need_realloc(in): 0-> initial allocation (malloc), otherwise "realloc"
153  *
154  * NOTE:This function allocates the memory for the log info area of the
155  * target transaction. It is called when the transaction tries to to
156  * insert/update/delete operation. If the transaction do read operation
157  * only, no memory is allocated.
158  *
159  * The allocation size is defined by a constant - REPL_LOG_INFO_ALLOC_SIZE
160  * We need to set the size for the user request ?
161  */
162 static int
163 repl_log_info_alloc (LOG_TDES * tdes, int arr_size, bool need_realloc)
164 {
165  int i = 0, k;
166  int error = NO_ERROR;
167 
168  if (need_realloc == false)
169  {
170  i = arr_size * DB_SIZEOF (LOG_REPL_RECORD);
171  tdes->repl_records = (LOG_REPL_RECORD *) malloc (i);
172  if (tdes->repl_records == NULL)
173  {
174  error = ER_REPL_ERROR;
175  er_set (ER_WARNING_SEVERITY, ARG_FILE_LINE, ER_REPL_ERROR, 1, "can't allocate memory");
176  return error;
177  }
178  tdes->num_repl_records = arr_size;
179  k = 0;
180  }
181  else
182  {
183  i = tdes->num_repl_records + arr_size;
184  tdes->repl_records = (LOG_REPL_RECORD *) realloc (tdes->repl_records, i * DB_SIZEOF (LOG_REPL_RECORD));
185  if (tdes->repl_records == NULL)
186  {
187  error = ER_REPL_ERROR;
188  er_set (ER_WARNING_SEVERITY, ARG_FILE_LINE, ER_REPL_ERROR, 1, "can't allocate memory");
189  return error;
190  }
191  k = tdes->num_repl_records;
192  tdes->num_repl_records = i;
193  }
194 
195  for (i = k; i < tdes->num_repl_records; i++)
196  {
197  tdes->repl_records[i].repl_data = NULL;
198  }
199 
200  return error;
201 }
202 
203 /*
204  * repl_add_update_lsa - update the LSA of the target transaction lo
205  *
206  * return: NO_ERROR or error code
207  *
208  * inst_oid(in): OID of the instance
209  *
210  * NOTE:For update operation, the server does "Heap stuff" after "Index Stuff".
211  * In order to reduce the cost of replication log, we generates a
212  * replication log at the point of indexing processing step.
213  * (During index processing, the primary key value is fetched ..)
214  * After Heap operation, we have to set the target LSA into the
215  * replication log.
216  *
217  * For update case, this function is called by locator_update_force().
218  * In the case of insert/delete cases, when the replication log info. is
219  * generated, the server already has the target transaction log(HEAP_INSERT
220  * or HEAP_DELETE).
221  * But, for the udpate case, the server doesn't has the target log when
222  * it generates the replication log. So, the server has to find out the
223  * location of replication record and match with the target transaction
224  * log after heap_update(). This is done by locator_update_force().
225  */
226 int
227 repl_add_update_lsa (THREAD_ENTRY * thread_p, const OID * inst_oid)
228 {
229  int tran_index;
230  LOG_TDES *tdes;
231  LOG_REPL_RECORD *repl_rec;
232  int i;
233  bool find = false;
234  int error = NO_ERROR;
235 
236  tran_index = LOG_FIND_THREAD_TRAN_INDEX (thread_p);
237 
238  tdes = LOG_FIND_TDES (tran_index);
239  if (tdes == NULL)
240  {
241  return ER_FAILED;
242  }
243 
244  /* If suppress_replication flag is set, do not write replication log. */
245  if (tdes->suppress_replication != 0)
246  {
247  return NO_ERROR;
248  }
249 
250  for (i = tdes->cur_repl_record - 1; i >= 0; i--)
251  {
252  repl_rec = (LOG_REPL_RECORD *) (&tdes->repl_records[i]);
253  if (OID_EQ (&repl_rec->inst_oid, inst_oid) && !LSA_ISNULL (&tdes->repl_update_lsa))
254  {
255  assert (repl_rec->rcvindex == RVREPL_DATA_UPDATE || repl_rec->rcvindex == RVREPL_DATA_UPDATE_START
256  || repl_rec->rcvindex == RVREPL_DATA_UPDATE_END);
257  if (repl_rec->rcvindex == RVREPL_DATA_UPDATE || repl_rec->rcvindex == RVREPL_DATA_UPDATE_START
258  || repl_rec->rcvindex == RVREPL_DATA_UPDATE_END)
259  {
260  LSA_COPY (&repl_rec->lsa, &tdes->repl_update_lsa);
261  LSA_SET_NULL (&tdes->repl_update_lsa);
262  LSA_SET_NULL (&tdes->repl_insert_lsa);
263  find = true;
264  break;
265  }
266  }
267  }
268 
269  if (find == false && prm_get_bool_value (PRM_ID_DEBUG_REPLICATION_DATA))
270  {
271  _er_log_debug (ARG_FILE_LINE, "can't find out the UPDATE LSA");
272  }
273 
274  return error;
275 }
276 
277 /*
278  * repl_log_insert - insert a replication info to the transaction descriptor
279  *
280  * return: NO_ERROR or error code
281  *
282  * class_oid(in): OID of the class
283  * inst_oid(in): OID of the instance
284  * log_type(in): log type (DATA or SCHEMA)
285  * rcvindex(in): recovery index (INSERT or DELETE or UPDATE)
286  * key_dbvalue(in): Primary Key value
287  *
288  * NOTE:insert a replication log info to the transaction descriptor (tdes)
289  */
290 int
291 repl_log_insert (THREAD_ENTRY * thread_p, const OID * class_oid, const OID * inst_oid, LOG_RECTYPE log_type,
292  LOG_RCVINDEX rcvindex, DB_VALUE * key_dbvalue, REPL_INFO_TYPE repl_info)
293 {
294  int tran_index;
295  LOG_TDES *tdes;
296  LOG_REPL_RECORD *repl_rec;
298  char *class_name = NULL;
299  char *ptr;
300  int error = NO_ERROR, strlen;
301 
302  tran_index = LOG_FIND_THREAD_TRAN_INDEX (thread_p);
303  tdes = LOG_FIND_TDES (tran_index);
304  if (tdes == NULL)
305  {
306  return ER_FAILED;
307  }
308 
309  /* If suppress_replication flag is set, do not write replication log. */
310  if (tdes->suppress_replication != 0)
311  {
312  /* clear repl lsa in tdes since no replication log will be written */
313  LSA_SET_NULL (&tdes->repl_insert_lsa);
314  LSA_SET_NULL (&tdes->repl_update_lsa);
315 
316  return NO_ERROR;
317  }
318 
319  if (thread_p->no_logging && tdes->fl_mark_repl_recidx == -1)
320  {
321  return NO_ERROR;
322  }
323 
324  /* check the replication log array status, if we need to alloc? */
325  if (REPL_LOG_IS_NOT_EXISTS (tran_index)
326  && ((error = repl_log_info_alloc (tdes, REPL_LOG_INFO_ALLOC_SIZE, false)) != NO_ERROR))
327  {
328  return error;
329  }
330  /* the replication log array is full? re-alloc? */
331  else if (REPL_LOG_IS_FULL (tran_index)
332  && (error = repl_log_info_alloc (tdes, REPL_LOG_INFO_ALLOC_SIZE, true)) != NO_ERROR)
333  {
334  return error;
335  }
336 
337  repl_rec = (LOG_REPL_RECORD *) (&tdes->repl_records[tdes->cur_repl_record]);
338  repl_rec->repl_type = log_type;
339  repl_rec->tde_encrypted = false;
340 
341  repl_rec->rcvindex = rcvindex;
342  if (rcvindex == RVREPL_DATA_UPDATE)
343  {
344  switch (repl_info)
345  {
347  repl_rec->rcvindex = RVREPL_DATA_UPDATE_START;
348  break;
350  repl_rec->rcvindex = RVREPL_DATA_UPDATE_END;
351  break;
353  default:
354  break;
355  }
356 
357  }
358  COPY_OID (&repl_rec->inst_oid, inst_oid);
359 
360  /* make the common info for the data replication */
361  if (log_type == LOG_REPLICATION_DATA)
362  {
363  char *ptr_to_packed_key_value_size = NULL;
364  int packed_key_len = 0;
365 
366  if (heap_get_class_name (thread_p, class_oid, &class_name) != NO_ERROR || class_name == NULL)
367  {
368  ASSERT_ERROR_AND_SET (error);
369  if (error == NO_ERROR)
370  {
371  error = ER_REPL_ERROR;
372  er_set (ER_WARNING_SEVERITY, ARG_FILE_LINE, ER_REPL_ERROR, 1, "can't get class_name");
373  }
374  return error;
375  }
376 
377  if (heap_get_class_tde_algorithm (thread_p, class_oid, &tde_algo) != NO_ERROR)
378  {
379  ASSERT_ERROR_AND_SET (error);
380  if (error == NO_ERROR)
381  {
382  error = ER_REPL_ERROR;
383  }
384  return error;
385  }
386 
387  repl_rec->tde_encrypted = tde_algo != TDE_ALGORITHM_NONE;
388 
389  repl_rec->length = OR_INT_SIZE; /* packed_key_value_size */
390  repl_rec->length += or_packed_string_length (class_name, &strlen);
391  repl_rec->length += OR_VALUE_ALIGNED_SIZE (key_dbvalue);
392 
393  ptr = (char *) malloc (repl_rec->length);
394  if (ptr == NULL)
395  {
396  error = ER_REPL_ERROR;
397  er_set (ER_WARNING_SEVERITY, ARG_FILE_LINE, ER_REPL_ERROR, 1, "can't allocate memory");
398  free_and_init (class_name);
399  return error;
400  }
401 
402 #if !defined (NDEBUG)
403  /* Suppress valgrind complaint. */
404  memset (ptr, 0, repl_rec->length);
405 #endif // DEBUG
406 
407  repl_rec->repl_data = ptr;
408 
409  /* first 4 bytes are for packed_key_len which will be filled after packing the value. */
410  ptr_to_packed_key_value_size = ptr;
411  ptr += OR_INT_SIZE;
412 
413  ptr = or_pack_string_with_length (ptr, class_name, strlen);
414  ptr = or_pack_mem_value (ptr, key_dbvalue, &packed_key_len);
415 
416  /* fill the length of disk image of pk */
417  or_pack_int (ptr_to_packed_key_value_size, packed_key_len);
418  }
419  else
420  {
421  repl_rec->repl_data = NULL;
422  repl_rec->length = 0;
423  }
424  repl_rec->must_flush = LOG_REPL_COMMIT_NEED_FLUSH;
425 
426  switch (rcvindex)
427  {
428  case RVREPL_DATA_INSERT:
429  if (!LSA_ISNULL (&tdes->repl_insert_lsa))
430  {
431  LSA_COPY (&repl_rec->lsa, &tdes->repl_insert_lsa);
432  LSA_SET_NULL (&tdes->repl_insert_lsa);
433  LSA_SET_NULL (&tdes->repl_update_lsa);
434  }
435  break;
436  case RVREPL_DATA_UPDATE:
437  /*
438  * for the update case, this function is called before the heap
439  * file update, so we don't need to LSA for update log here.
440  */
441  LSA_SET_NULL (&repl_rec->lsa);
442  break;
443  case RVREPL_DATA_DELETE:
444  /*
445  * for the delete case, we don't need to find out the target
446  * LSA. Delete is operation is possible without "After Image"
447  */
448  if (LSA_ISNULL (&tdes->tail_lsa))
449  {
450  LSA_COPY (&repl_rec->lsa, &log_Gl.prior_info.prior_lsa);
451  }
452  else
453  {
454  LSA_COPY (&repl_rec->lsa, &tdes->tail_lsa);
455  }
456  break;
457  default:
458  break;
459  }
460  tdes->cur_repl_record++;
461 
462  /* if flush marking is started, mark "must_flush" at current log except the log conflicts with previous logs due to
463  * same instance update */
464  if (tdes->fl_mark_repl_recidx != -1)
465  {
466  LOG_REPL_RECORD *recsp = tdes->repl_records;
467  int i;
468 
469  if (strcmp (class_name, CT_SERIAL_NAME) != 0)
470  {
471  for (i = 0; i < tdes->fl_mark_repl_recidx; i++)
472  {
473  if (recsp[i].must_flush == LOG_REPL_COMMIT_NEED_FLUSH && OID_EQ (&recsp[i].inst_oid, &repl_rec->inst_oid))
474  {
475  break;
476  }
477  }
478 
479  if (i >= tdes->fl_mark_repl_recidx)
480  {
481  repl_rec->must_flush = LOG_REPL_NEED_FLUSH;
482  }
483  }
484  else
485  {
486  repl_rec->must_flush = LOG_REPL_NEED_FLUSH;
487  }
488  }
489 
490  if (class_name != NULL)
491  {
492  free_and_init (class_name);
493  }
494 
495  return error;
496 }
497 
498 /*
499  * repl_log_insert_schema - insert a replication info(schema) to the
500  * transaction descriptor
501  *
502  * return: NO_ERROR or error code
503  *
504  * repl_schema(in):
505  *
506  * NOTE:insert a replication log info(schema) to the transaction
507  * descriptor (tdes)
508  */
509 int
510 repl_log_insert_statement (THREAD_ENTRY * thread_p, REPL_INFO_SBR * repl_info)
511 {
512  int tran_index;
513  LOG_TDES *tdes;
514  LOG_REPL_RECORD *repl_rec;
515  char *ptr;
516  int error = NO_ERROR, strlen1, strlen2, strlen3, strlen4;
517 
518  tran_index = LOG_FIND_THREAD_TRAN_INDEX (thread_p);
519  tdes = LOG_FIND_TDES (tran_index);
520  if (tdes == NULL)
521  {
522  return ER_FAILED;
523  }
524 
525  /* If suppress_replication flag is set, do not write replication log. */
526  if (tdes->suppress_replication != 0)
527  {
528  return NO_ERROR;
529  }
530 
531  /* check the replication log array status, if we need to alloc? */
532  if (REPL_LOG_IS_NOT_EXISTS (tran_index)
533  && ((error = repl_log_info_alloc (tdes, REPL_LOG_INFO_ALLOC_SIZE, false)) != NO_ERROR))
534  {
535  return error;
536  }
537  /* the replication log array is full? re-alloc? */
538  else if (REPL_LOG_IS_FULL (tran_index)
539  && (error = repl_log_info_alloc (tdes, REPL_LOG_INFO_ALLOC_SIZE, true)) != NO_ERROR)
540  {
541  return error;
542  }
543 
544  repl_rec = (LOG_REPL_RECORD *) (&tdes->repl_records[tdes->cur_repl_record]);
545  repl_rec->repl_type = LOG_REPLICATION_STATEMENT;
546  repl_rec->tde_encrypted = false;
547 
548  repl_rec->rcvindex = RVREPL_STATEMENT;
549  repl_rec->must_flush = LOG_REPL_COMMIT_NEED_FLUSH;
550  OID_SET_NULL (&repl_rec->inst_oid);
551 
552  /* make the common info for the schema replication */
553  repl_rec->length = (OR_INT_SIZE /* REPL_INFO_SCHEMA.statement_type */
554  + or_packed_string_length (repl_info->name, &strlen1)
555  + or_packed_string_length (repl_info->stmt_text, &strlen2)
556  + or_packed_string_length (repl_info->db_user, &strlen3)
557  + or_packed_string_length (repl_info->sys_prm_context, &strlen4));
558 
559  repl_rec->repl_data = (char *) malloc (repl_rec->length);
560  if (repl_rec->repl_data == NULL)
561  {
562  error = ER_REPL_ERROR;
563  er_set (ER_WARNING_SEVERITY, ARG_FILE_LINE, ER_REPL_ERROR, 1, "can't allocate memory");
564  return error;
565  }
566  ptr = repl_rec->repl_data;
567  ptr = or_pack_int (ptr, repl_info->statement_type);
568  ptr = or_pack_string_with_length (ptr, repl_info->name, strlen1);
569  ptr = or_pack_string_with_length (ptr, repl_info->stmt_text, strlen2);
570  ptr = or_pack_string_with_length (ptr, repl_info->db_user, strlen3);
571  ptr = or_pack_string_with_length (ptr, repl_info->sys_prm_context, strlen4);
572 
574  {
576  "repl_log_insert_statement: repl_info_sbr { type %d, name %s, stmt_txt %s, user %s, "
577  "sys_prm_context %s }\n", repl_info->statement_type, repl_info->name, repl_info->stmt_text,
578  repl_info->db_user, repl_info->sys_prm_context);
579  }
580  LSA_COPY (&repl_rec->lsa, &tdes->tail_lsa);
581 
582  if (tdes->fl_mark_repl_recidx != -1 && tdes->cur_repl_record >= tdes->fl_mark_repl_recidx)
583  {
584  /*
585  * statement replication does not check log conflicts, so
586  * use repl_start_flush_mark with caution.
587  */
588  repl_rec->must_flush = LOG_REPL_NEED_FLUSH;
589  }
590 
591  tdes->cur_repl_record++;
592 
593  return error;
594 }
595 
596 /*
597  * repl_start_flush_mark -
598  *
599  * return:
600  *
601  * NOTE:start to mark "must_flush" for repl records to be appended after this
602  */
603 void
604 repl_start_flush_mark (THREAD_ENTRY * thread_p)
605 {
606  LOG_TDES *tdes;
607 
608  tdes = LOG_FIND_CURRENT_TDES (thread_p);
609 
610  if (tdes == NULL)
611  {
613  LOG_FIND_THREAD_TRAN_INDEX (thread_p));
614  return;
615  }
616  if (tdes->fl_mark_repl_recidx == -1)
617  {
618  tdes->fl_mark_repl_recidx = tdes->cur_repl_record;
619  } /* else already started, return */
620  return;
621 }
622 
623 /*
624  * repl_end_flush_mark -
625  *
626  * return:
627  *
628  * need_undo(in):
629  *
630  * NOTE:end to mark "must_flush" for repl records
631  */
632 void
633 repl_end_flush_mark (THREAD_ENTRY * thread_p, bool need_undo)
634 {
635  LOG_TDES *tdes;
636  int i;
637 
638  tdes = LOG_FIND_CURRENT_TDES (thread_p);
639 
640  if (tdes == NULL)
641  {
643  LOG_FIND_THREAD_TRAN_INDEX (thread_p));
644  return;
645  }
646  if (need_undo)
647  {
648  LOG_REPL_RECORD *recsp = tdes->repl_records;
649  for (i = tdes->fl_mark_repl_recidx; i < tdes->cur_repl_record; i++)
650  {
651  /* initialize repl records to be marked as flush */
652  free_and_init (recsp[i].repl_data);
653  }
654  tdes->cur_repl_record = tdes->fl_mark_repl_recidx;
655  }
656  tdes->fl_mark_repl_recidx = -1;
657 
658  return;
659 }
660 
661 /*
662  * repl_log_abort_after_lsa -
663  *
664  * return:
665  *
666  * tdes (in) :
667  * start_lsa (in) :
668  *
669  */
670 int
671 repl_log_abort_after_lsa (LOG_TDES * tdes, LOG_LSA * start_lsa)
672 {
673  LOG_REPL_RECORD *repl_rec_arr;
674  int i;
675 
676  repl_rec_arr = tdes->repl_records;
677  for (i = 0; i < tdes->cur_repl_record; i++)
678  {
679  if (LSA_GT (&repl_rec_arr[i].lsa, start_lsa))
680  {
681  repl_rec_arr[i].must_flush = LOG_REPL_DONT_NEED_FLUSH;
682  }
683  }
684 
685  return NO_ERROR;
686 }
687 
688 #if defined(CUBRID_DEBUG)
689 /*
690  * repl_debug_info - DEBUGGING Function, print out the replication log info.
691  *
692  * return:
693  *
694  * NOTE:Dump the replication log info to the stdout.
695  */
696 void
697 repl_debug_info ()
698 {
699  LOG_TDES *tdes;
700  LOG_REPL_RECORD *repl_rec;
701  int tnum, rnum;
702  char *class_name;
703  DB_VALUE key;
704  char *ptr;
705 
706  fprintf (stdout, "REPLICATION LOG DUMP -- Memory\n");
707  for (tnum = 0; tnum < log_Gl.trantable.num_assigned_indices; tnum++)
708  {
709  fprintf (stdout, "*************************************************\n");
710  tdes = log_Gl.trantable.all_tdes[tnum];
711  fprintf (stdout, "For the Trid : %d\n", (int) tdes->trid);
712  for (rnum = 0; rnum < tdes->cur_repl_record; rnum++)
713  {
714  fprintf (stdout, " RECORD # %d\n", rnum);
715  repl_rec = (LOG_REPL_RECORD *) (&tdes->repl_records[rnum]);
716  fprintf (stdout, " type: %s\n", log_to_string (repl_rec->repl_type));
717  fprintf (stdout, " OID: %d - %d - %d\n", repl_rec->inst_oid.volid, repl_rec->inst_oid.pageid,
718  repl_rec->inst_oid.slotid);
719  ptr = or_unpack_string_nocopy (repl_rec->repl_data, &class_name);
720  ptr = or_unpack_mem_value (ptr, &key);
721  fprintf (stdout, " class_name: %s\n", class_name);
722  fprintf (stdout, " LSA: %lld | %d\n", repl_rec->lsa.pageid, repl_rec->lsa.offset);
723  db_value_print (&key);
724  fprintf (stdout, "\n----------------------------------------------\n");
725  pr_clear_value (&key);
726  }
727  }
728  fflush (stdout);
729 }
730 #endif /* CUBRID_DEBUG */
731 
732 #endif /* SERVER_MODE || SA_MODE */
#define NO_ERROR
Definition: error_code.h:46
int cur_repl_record
Definition: log_impl.h:506
TRANTABLE trantable
Definition: log_impl.h:650
REPL_INFO_TYPE
Definition: replication.h:43
#define REPL_LOG_IS_NOT_EXISTS(tran_index)
Definition: replication.c:41
void LSA_COPY(log_lsa *plsa1, const log_lsa *plsa2)
Definition: log_lsa.hpp:139
LOG_LSA repl_update_lsa
Definition: log_impl.h:511
LOG_RCVINDEX
Definition: recovery.h:36
#define ER_FAILED
Definition: error_code.h:47
LOG_GLOBAL log_Gl
int num_repl_records
Definition: log_impl.h:505
#define ASSERT_ERROR_AND_SET(error_code)
int num_assigned_indices
Definition: log_impl.h:582
LOG_LSA tail_lsa
Definition: log_impl.h:473
#define OID_SET_NULL(oidp)
Definition: oid.h:85
LOG_TDES * LOG_FIND_TDES(int tran_index)
Definition: log_impl.h:1095
char * or_unpack_string_nocopy(char *ptr, char **string)
#define ER_REPL_ERROR
Definition: error_code.h:1121
void _er_log_debug(const char *file_name, const int line_no, const char *fmt,...)
#define COPY_OID(dest_oid_ptr, src_oid_ptr)
Definition: oid.h:63
void THREAD_ENTRY
const char * log_to_string(LOG_RECTYPE type)
Definition: log_manager.c:343
#define CT_SERIAL_NAME
Definition: transform.h:135
LOG_TDES ** all_tdes
Definition: log_impl.h:595
int heap_get_class_tde_algorithm(THREAD_ENTRY *thread_p, const OID *class_oid, TDE_ALGORITHM *tde_algo)
Definition: heap_file.c:10737
void er_set(int severity, const char *file_name, const int line_no, int err_id, int num_args,...)
#define assert(x)
TDE_ALGORITHM
Definition: tde.h:71
int or_packed_string_length(const char *string, int *strlen)
#define REPL_LOG_IS_FULL(tran_index)
Definition: replication.c:43
#define OR_VALUE_ALIGNED_SIZE(value)
enum log_rectype LOG_RECTYPE
Definition: log_record.hpp:138
#define OID_EQ(oidp1, oidp2)
Definition: oid.h:92
#define DB_SIZEOF(val)
Definition: memory_alloc.h:54
#define NULL
Definition: freelistheap.h:34
void db_value_print(const DB_VALUE *value)
Definition: db_macro.c:1663
bool LSA_ISNULL(const log_lsa *lsa_ptr)
Definition: log_lsa.hpp:153
char * or_unpack_int(char *ptr, int *number)
LOG_PRIOR_LSA_INFO prior_info
Definition: log_impl.h:652
#define ER_LOG_UNKNOWN_TRANINDEX
Definition: error_code.h:913
int pr_clear_value(DB_VALUE *value)
char * or_unpack_mem_value(char *buf, DB_VALUE *value)
char * or_pack_mem_value(char *ptr, DB_VALUE *value, int *packed_len_except_alignment)
struct log_repl * repl_records
Definition: log_impl.h:509
static void error(const char *msg)
Definition: gencat.c:331
static const int REPL_LOG_INFO_ALLOC_SIZE
Definition: replication.c:47
char * or_pack_int(char *ptr, int number)
LOG_TDES * LOG_FIND_CURRENT_TDES(THREAD_ENTRY *thread_p=NULL)
Definition: log_impl.h:1115
#define LOG_FIND_THREAD_TRAN_INDEX(thrd)
Definition: perf_monitor.h:158
int fl_mark_repl_recidx
Definition: log_impl.h:508
#define ARG_FILE_LINE
Definition: error_manager.h:44
#define free_and_init(ptr)
Definition: memory_alloc.h:147
LOG_LSA repl_insert_lsa
Definition: log_impl.h:510
#define strlen(s1)
Definition: intl_support.c:43
void LSA_SET_NULL(log_lsa *lsa_ptr)
Definition: log_lsa.hpp:146
char * or_pack_string_with_length(char *ptr, const char *string, int length)
TRANID trid
Definition: log_impl.h:466
bool LSA_GT(const log_lsa *plsa1, const log_lsa *plsa2)
Definition: log_lsa.hpp:188
int suppress_replication
Definition: log_impl.h:514
bool prm_get_bool_value(PARAM_ID prm_id)
int i
Definition: dynamic_load.c:954
int heap_get_class_name(THREAD_ENTRY *thread_p, const OID *class_oid, char **class_name)
Definition: heap_file.c:9328