IDA C++ SDK 9.2
Loading...
Searching...
No Matches
diff3.hpp
Go to the documentation of this file.
1/*
2 * Interactive disassembler (IDA).
3 * Copyright (c) 2005-2026 Hex-Rays SA <support@hex-rays.com>
4 * ALL RIGHTS RESERVED.
5 */
6
7#ifndef _DIFF3_HPP
8#define _DIFF3_HPP
9
21
22// The diffing algorithms in this file match information tied to addresses.
23// So, if addresses do not match, the information will be considered to be different.
24
25//-------------------------------------------------------------------------
30{
34 bool empty() const { return start >= end; }
35 void clear() { start = end = 0; }
36 bool contains(diffpos_t p) const { return start <= p && p < end; }
38 {
39 start = p;
40 if ( end < start )
41 end = start;
42 }
44 {
45 end = p;
46 if ( end < start )
47 start = end;
48 }
49 void intersect(const diff_range_t &r)
50 {
51 if ( start < r.start )
52 start = r.start;
53 if ( end > r.end )
54 end = r.end;
55 if ( end < start )
56 end = start;
57 }
58
59 int compare(const diff_range_t &r) const { return start > r.start ? 1 : start < r.start ? -1 : 0; }
60
61 bool operator ==(const diff_range_t &r) const { return compare(r) == 0; }
62 bool operator !=(const diff_range_t &r) const { return compare(r) != 0; }
63};
65
66//------------------------------------------------------------------------
81
82//------------------------------------------------------------------------
90
91//------------------------------------------------------------------------
104
105//------------------------------------------------------------------------
113
114//------------------------------------------------------------------------
115struct diff_text_t : public qstrvec_t
116{
118};
121
122//--------------------------------------------------------------------------
131
132//------------------------------------------------------------------------
133#ifndef SWIG
134#define DECLARE_DIFF_SOURCE_HELPERS(decl)\
135decl void ida_export diff_source_merge_region(class diff_source_t *destination, class diff_source_t *source, const diff_range_t &dr);
136#else
137#define DECLARE_DIFF_SOURCE_HELPERS(decl)
138#endif // SWIG
139
141
142//------------------------------------------------------------------------
148class diff_source_t
149{
150 friend class diff3_engine_t;
151 diffpos_t get_lastpos(const diff_range_t &r)
152 {
153 diffpos_t last = check_position(r.end, DIFFPOS_BACKWARD);
154 if ( last < r.start )
155 last = r.end;
156 if ( last == BADDIFF )
157 last = r.start;
158 return last;
159 }
160
161 void _merge_region(diff_source_t *source, const diff_range_t &dr);
162
164
165public:
166 int dbctx_id;
167 diff_source_idx_t diffidx = NONE_IDX;
169 diff_source_t(int id) : dbctx_id(id) {}
170
171 virtual ~diff_source_t() {}
172
181 virtual void init_diff_source() {}
182
184 virtual void set_range(const diff_range_t &r) { range = r; }
185
187 virtual const diff_range_t &get_range() const { return range; }
188
192 virtual diffpos_t check_position(diffpos_t dpos, diffpos_check_t adj=DIFFPOS_CHECK) const = 0;
193
199 virtual diff_degree_t compare_chunks(diff_source_t *src2, diffpos_t dpos) const = 0;
200
210 virtual diff_degree_t find_next_diffpos(
211 diffpos_t * /*dpos1*/,
212 diffpos_t * /*dpos2*/,
213 diff_source_t * /*src2*/) const
214 {
215 return -1; // not implemented
216 }
217
220 virtual qstring print_diffpos_name(diffpos_t dpos) const = 0;
221
225 virtual void print_diffpos_details(qstrvec_t * /*out*/, diffpos_t /*dpos*/) const {}
226
230 virtual void merge_add(diff_source_t * /*src*/, diffpos_t /*dpos*/) {}
231
233 virtual void merge_del(diffpos_t /*dpos*/) {}
234
237 virtual void merge_replace(diff_source_t *src, diffpos_t dpos)
238 {
239 merge_del(dpos);
240 merge_add(src, dpos);
241 }
242
247 virtual void merge_region(diff_source_t *src, const diff_range_t &region)
248 {
249 diff_source_merge_region(this, src, region);
250 }
251
252#ifdef TESTABLE_BUILD
253 // dump the test results into the provided log file.
254 // nb: there is no need to switch dbctx, it is already done.
255 virtual void dump_merge_results(FILE * /*fp*/) const {}
256#endif
257
258 diff_texts_t print_range(const diff_range_t *r, bool with_details) const;
259 void test_diffpos_behavior() const;
260 bool is_valid_position(diffpos_t dpos) const
261 {
262 return get_range().contains(dpos) && check_position(dpos) == dpos;
263 }
264 diff_texts_t print_diff_source(bool with_details=true) const
265 {
266 return print_range(nullptr, with_details);
267 }
268};
269
270//------------------------------------------------------------------------
271enum merge_policy_t ENUM_SIZE(uint8)
272{
273 MERGE_POLICY_SKIP,
274 MERGE_POLICY_USE_LOCAL,
275 MERGE_POLICY_USE_REMOTE,
276 MERGE_POLICY_POSTPONE,
277 MERGE_POLICY_MDIFF,
278 MERGE_POLICY_VDIFF,
279 MERGE_POLICY_LAST,
280};
281
282//------------------------------------------------------------------------
287{
288 diff_source_t *src1;
289 diff_source_t *src2;
291 diff_result_t(diff_source_t *s1=nullptr, diff_source_t *s2=nullptr) : src1(s1), src2(s2) {}
292 qstrvec_t print_region(const diff_region_t &b, bool with_details=true) const;
293 qstrvec_t print_diff_result(bool with_details=true) const;
294 size_t size() const { return regions.size(); }
295 bool empty() const { return regions.empty(); }
296
303 size_t merge_diff_sources(merge_policy_t merge_policy, size_t i1=0, size_t i2=SIZE_MAX);
304private:
305 bool merge_one_region(size_t n, merge_policy_t merge_policy) const;
306};
307
308//------------------------------------------------------------------------
309typedef void (*diff_progress_cb_t)(diffpos_t pos, const diff_range_t &range, void *ud);
310
315{
317 void *ud = nullptr;
319
321 diff_progress_t(diff_progress_cb_t _cb, void *_ud) : cb(_cb), ud(_ud) {}
322};
323
324//------------------------------------------------------------------------
328{
329 friend class diff3_engine_t;
330protected:
331 diff_source_t *src1;
332 diff_source_t *src2;
334
335public:
336 diff_engine_t(diff_source_t *_src1, diff_source_t *_src2)
337 : src1(_src1), src2(_src2)
338 {
339 }
340 virtual ~diff_engine_t() {}
341 virtual bool get_diff_regions(diff_regions_t *out) = 0;
342 virtual void set_progress(diff_progress_t *p) { progress = p; }
344};
345
346//------------------------------------------------------------------------
352{
353 // we maintain two positions to optimize calls to adjust_position
354 // if you decide to remove one of them, please ensure that
355 // std::lower_bound in testdiff3.cpp is not called too often
356 diffpos_t pos1;
357 diffpos_t pos2;
358 diff_degree_t calc_diff_degree(diff_degree_t cur_degree);
359public:
360 diff2_engine_t(diff_source_t *_src1, diff_source_t *_src2)
361 : diff_engine_t(_src1, _src2)
362 {
363 reset();
364 }
365 void reset();
366 virtual bool get_diff_regions(diff_regions_t *out) override;
368};
369
370//------------------------------------------------------------------------
376{
377 diff2_engine_t de1;
378 diff2_engine_t de2;
379 diff2_engine_t de3;
380
381public:
383 diff_source_t *base,
384 diff_source_t *src1,
385 diff_source_t *src2);
386 virtual ~diff3_engine_t() {}
387 virtual bool get_diff_regions(diff_regions_t *out) override;
388 virtual void set_progress(diff_progress_t *p) override
389 {
391 de1.set_progress(p);
392 de2.set_progress(p);
393 de3.set_progress(p);
394 }
395};
396
403 diff_source_t *base,
404 diff_source_t *src1,
405 diff_source_t *src2,
406 diff_progress_t *progress=nullptr);
407
409 const char *const *headers,
410 const diff_texts_t *const *linevecs,
411 size_t n,
412 int psbs_flags=0);
413#define PSBS_DIFF_STARS 0x01
414#define PSBS_ONLY_DIFFS 0x02
415
416//-------------------------------------------------------------------------
425
426//-------------------------------------------------------------------------
430
432template<class T>
434{
438
440
441 void append(const T &v, size_t idx) { part.push_back(v[idx]); }
442 void reverse() { std::reverse(part.begin(), part.end()); }
443};
444// template specialisation for qstring vector
445template<>
447{
451
453
454 void append(const qstring &v, size_t idx) { part.append(v[idx]); }
455 void reverse() { if ( !part.empty() ) std::reverse(part.begin(), std::prev(part.end())); }
456};
459
461template<class T>
462class lcsdiff_res_t : public qvector<lcsdiff_res_part_t<T>>
463{
464public:
466 void eq(const T &v, size_t idx)
467 {
468 lcsdiff_res_part_t<T> &part = set_action(TDLA_EQ);
469 part.append(v, idx);
470 }
471
473 void add(const T &v, size_t idx)
474 {
475 lcsdiff_res_part_t<T> &part = set_action(TDLA_ADD);
476 part.append(v, idx);
477 }
478
480 void sub(const T &v, size_t idx)
481 {
482 lcsdiff_res_part_t<T> &part = set_action(TDLA_SUB);
483 part.append(v, idx);
484 }
485
486private:
487 lcsdiff_res_part_t<T> &set_action(lcsdiff_result_action_t wanted_action)
488 {
489 if ( this->empty() || this->back().action != wanted_action )
490 this->push_back(lcsdiff_res_part_t<T>(wanted_action));
491 return this->back();
492 }
493};
494
495//-------------------------------------------------------------------------
499template<class T>
501{
502protected:
503 const T &x;
504 const T &y;
505 const size_t n = 0;
506 const size_t m = 0;
508
509public:
512
513 //------------------------------------------------------------------
515 lcsdiff_t(const T &_x, const T &_y, size_t _n, size_t _m)
516 : x(_x),
517 y(_y),
518 n(_n),
519 m(_m)
520 {
521 // allocate storage for TABLE
522 // need an additional row/column at index 0
523 const size_t rows = n + 1;
524 const size_t cols = m + 1;
525 lcs_table.resize(rows * cols);
526
527 // compute the LCS for substring started from (i,j) indices
528 for ( size_t i=0; i < rows; ++i )
529 {
530 for ( size_t j=0; j < cols; ++j )
531 {
532 if ( i == 0 || j == 0 )
533 {
534 table(i, j) = 0;
535 }
536 else if ( x[i - 1] == y[j - 1] )
537 {
538 table(i, j) = 1 + table(i - 1, j - 1);
539 }
540 else
541 {
542 size_t l = table(i - 1, j);
543 size_t u = table(i, j - 1);
544 table(i, j) = qmax(l, u);
545 }
546 }
547 }
548 }
549
550 //------------------------------------------------------------------
553 void diff()
554 {
555 result.clear();
556 size_t i = n;
557 size_t j = m;
558 while ( i != 0 || j != 0 )
559 {
560 // end of seq reached
561 if ( i == 0 )
562 {
563 result.add(y, --j);
564 }
565 else if ( j == 0 )
566 {
567 result.sub(x, --i);
568 }
569 // Otherwise there's still parts of X and Y left. If the
570 // currently considered parts are equal, then we found an unchanged
571 // part which belongs to the longest common subsequence.
572 else if ( x[i - 1] == y[j - 1] )
573 {
574 result.eq(x, --i);
575 j--;
576 }
577 // In any other case, we go in the direction of the longest common subsequence.
578 else if ( table(i - 1, j) <= table(i, j - 1) )
579 {
580 result.add(y, --j);
581 }
582 else
583 {
584 result.sub(x, --i);
585 }
586 }
587 std::reverse(result.begin(), result.end());
588 for ( auto &part : result )
589 part.reverse();
590 }
591
592private:
593 size_t &table(size_t i, size_t j)
594 {
595 const size_t idx = i * (m + 1) + j;
596 QASSERT(2351, idx < lcs_table.size());
597 return lcs_table[idx];
598 }
599};
600
601//-------------------------------------------------------------------------
604{
606 {
609
610 // print lines
613
623 };
624
627
628 virtual void on_event(event_t ev, ...) = 0;
629};
630
631//-------------------------------------------------------------------------
632class txtdiff_t;
633
634#ifndef SWIG
635#define DECLARE_TXTDIFF_HELPERS(decl)\
636decl void ida_export txtdiff_t_diff_mod(txtdiff_t *_this);\
637decl void ida_export txtdiff_t_serialize(txtdiff_t *_this, txtdiff_printer_t &printer);
638#else
639#define DECLARE_TXTDIFF_HELPERS(decl)
640#endif // SWIG
641
642DECLARE_TXTDIFF_HELPERS(idaman)
643
644//------------------------------------------------------------------------
646class txtdiff_t : public lcsdiff_t<qstrvec_t>
647{
648public:
649 txtdiff_t(const qstrvec_t &_x, const qstrvec_t &_y)
650 : lcsdiff_t<qstrvec_t>(_x, _y, _x.size(), _y.size()) {}
651
652 //--------------------------------------------------------
656 void diff_mod() { txtdiff_t_diff_mod(this); }
657
658 //------------------------------------------------------------------------
661 void serialize(txtdiff_printer_t &printer) { txtdiff_t_serialize(this, printer); }
662
663 //--------------------------------------------------------
664 // Convenience methods
665
672 static void visual_diff(qstrvec_t *res, const qstrvec_t &x, const qstrvec_t &y, bool use_mod=true)
673 {
674 txtdiff_t d(x, y);
675 use_mod ? d.diff_mod() : d.diff();
676 for ( const auto &dl : d.result )
677 {
678 char c = dl.action == TDLA_EQ ? ' '
679 : dl.action == TDLA_ADD ? '+'
680 : dl.action == TDLA_SUB ? '-'
681 : '*'; // TDLA_MOD
682 for ( auto &p : dl.part )
683 res->push_back().sprnt("%c %s", c, p.c_str());
684 }
685 }
686
687private:
688 DECLARE_TXTDIFF_HELPERS(friend)
689 // do not call these functions directly, they are here only for exporting
690 void _diff_mod();
691 void _serialize(txtdiff_printer_t &printer);
692};
693#undef DECLARE_TXTDIFF_HELPERS
694
695//-------------------------------------------------------------------------
698{
711
714
715 virtual void on_event(event_t ev, ...) = 0;
716};
717
718//-------------------------------------------------------------------------
719class strdiff_t;
720
721#ifndef SWIG
722#define DECLARE_STRDIFF_HELPERS(decl)\
723decl void ida_export strdiff_t_serialize(strdiff_t *_this, strdiff_printer_t &printer);
724#else
725#define DECLARE_STRDIFF_HELPERS(decl)
726#endif // SWIG
727
728DECLARE_STRDIFF_HELPERS(idaman)
729
730//-------------------------------------------------------------------------
732class strdiff_t : public lcsdiff_t<qstring>
733{
734public:
735 strdiff_t(const qstring &_x, const qstring &_y)
736 : lcsdiff_t<qstring>(_x, _y, _x.length(), _y.length()) {}
737
738 //------------------------------------------------------------------------
740 void serialize(strdiff_printer_t &printer) { strdiff_t_serialize(this, printer); }
741
742private:
743 DECLARE_STRDIFF_HELPERS(friend)
744 // do not call these functions directly, they are here only for exporting
745 void _serialize(strdiff_printer_t &printer);
746};
747#undef DECLARE_STRDIFF_HELPERS
748#endif // _DIFF3_HPP
virtual bool get_diff_regions(diff_regions_t *out) override
diff2_engine_t(diff_source_t *_src1, diff_source_t *_src2)
Definition diff3.hpp:360
bool get_diff_region(diff_region_t *out)
A 3-way difference engine.
Definition diff3.hpp:376
virtual bool get_diff_regions(diff_regions_t *out) override
diff3_engine_t(diff_source_t *base, diff_source_t *src1, diff_source_t *src2)
virtual void set_progress(diff_progress_t *p) override
Definition diff3.hpp:388
virtual ~diff3_engine_t()
Definition diff3.hpp:386
virtual void set_progress(diff_progress_t *p)
Definition diff3.hpp:342
diff_source_t * src1
Definition diff3.hpp:331
diff_source_t * src2
Definition diff3.hpp:332
virtual ~diff_engine_t()
Definition diff3.hpp:340
diff_engine_t(diff_source_t *_src1, diff_source_t *_src2)
Definition diff3.hpp:336
virtual bool get_diff_regions(diff_regions_t *out)=0
diff_progress_t * progress
not owned; may be nullptr
Definition diff3.hpp:333
friend class diff3_engine_t
Definition diff3.hpp:329
diff_result_t perform_diff()
result
Definition diff3.hpp:463
void add(const T &v, size_t idx)
vector's item should be added
Definition diff3.hpp:473
void sub(const T &v, size_t idx)
vector's item should be deleted
Definition diff3.hpp:480
void eq(const T &v, size_t idx)
vector's items are equal
Definition diff3.hpp:466
Calculate difference between two vectors.
Definition diff3.hpp:501
const size_t n
left argument size
Definition diff3.hpp:505
lcsdiff_t(const T &_x, const T &_y, size_t _n, size_t _m)
prepare LCS table
Definition diff3.hpp:515
sizevec_t lcs_table
table to store LCS for each step of the calculation
Definition diff3.hpp:507
void diff()
get a difference between two vectors RESULT will contain only TDLA_EQ, TDLA_ADD, TDLA_SUB actions
Definition diff3.hpp:553
result_t result
Definition diff3.hpp:511
const size_t m
right argument size
Definition diff3.hpp:506
const T & y
right argument
Definition diff3.hpp:504
const T & x
left argument
Definition diff3.hpp:503
lcsdiff_res_t< T > result_t
Definition diff3.hpp:510
Reimplementation of vector class from STL.
Definition pro.h:2262
bool empty(void) const
Definition pro.h:2495
const T & back(void) const
Definition pro.h:2502
qvector(void)
Definition pro.h:2374
void push_back(T &&x)
Definition pro.h:2432
size_t size(void) const
Get the number of elements in the qvector.
Definition pro.h:2494
diffpos_check_t
Definition diff3.hpp:107
@ DIFFPOS_BACKWARD
back off to the previous valid position
Definition diff3.hpp:111
@ DIFFPOS_FORWARD
advance to the next valid position
Definition diff3.hpp:110
@ DIFFPOS_CHECK
verify if the position is valid; if not, return the next valid position
Definition diff3.hpp:108
diff_result_t perform_diff3(diff_source_t *base, diff_source_t *src1, diff_source_t *src2, diff_progress_t *progress=nullptr)
Perform 3-way difference.
qvector< diff_text_t > diff_texts_t
Definition diff3.hpp:120
DECLARE_DIFF_SOURCE_HELPERS(idaman) class diff_source_t
A difference source.
Definition diff3.hpp:140
enum merge_policy_t ENUM_SIZE(uint8)
Definition diff3.hpp:271
diff_source_idx_t
standard indexes into dbctx_ids[] and similar arrays
Definition diff3.hpp:125
@ BASE_IDX
Definition diff3.hpp:129
@ LOCAL_IDX
Definition diff3.hpp:127
@ NONE_IDX
Definition diff3.hpp:126
@ REMOTE_IDX
Definition diff3.hpp:128
lcsdiff_result_action_t
diff result actions, lcsdiff_t::diff lcsdiff_t::diff_mod
Definition diff3.hpp:419
@ TDLA_MOD
updated items (new content)
Definition diff3.hpp:423
@ TDLA_SUB
removed items
Definition diff3.hpp:422
@ TDLA_ADD
added items
Definition diff3.hpp:421
@ TDLA_EQ
items are equal
Definition diff3.hpp:420
qvector< diff_region_t > diff_regions_t
Definition diff3.hpp:103
diff_action_t
Definition diff3.hpp:84
@ DIFF_USE1
use information from src1
Definition diff3.hpp:86
@ DIFF_BOTH
use information from both (conflict)
Definition diff3.hpp:88
@ DIFF_USE2
use information from src2
Definition diff3.hpp:87
@ DIFF_NONE
unknown
Definition diff3.hpp:85
DECLARE_TYPE_AS_MOVABLE(diff_range_t)
void(* diff_progress_cb_t)(diffpos_t pos, const diff_range_t &range, void *ud)
Definition diff3.hpp:309
qstrvec_t put_side_by_side(const char *const *headers, const diff_texts_t *const *linevecs, size_t n, int psbs_flags=0)
ssize_t diff_degree_t
A difference degree.
Definition diff3.hpp:80
idaman size_t n
Definition pro.h:1000
cexpr_t * e
Definition hexrays.hpp:7705
idaman int64 pos
Definition kernwin.hpp:1398
asize_t size
Definition kernwin.hpp:6701
void(idaapi *range_marker)(ea_t ea
Pointer to range marker function (for idaviews and hexviews) This pointer is initialized by setup_ran...
unsigned __int64 uint64
Definition llong.hpp:13
qvector< qstring > qstrvec_t
Definition lumina.hpp:831
qvector< size_t > sizevec_t
vector of sizes
Definition pro.h:2841
size_t diffpos_t
Definition pro.h:483
ptrdiff_t ssize_t
Signed size_t - used to check for size overflows when the counter becomes negative.
Definition pro.h:385
constexpr diffpos_t BADDIFF
Definition pro.h:484
unsigned char uint8
unsigned 8 bit value
Definition pro.h:348
_qstring< char > qstring
regular string
Definition pro.h:3771
Diff progress reporting state (shared between diff engines).
Definition diff3.hpp:315
uint64 last_ns
last notification timestamp (internal)
Definition diff3.hpp:318
void * ud
Definition diff3.hpp:317
diff_progress_t()
Definition diff3.hpp:320
diff_progress_t(diff_progress_cb_t _cb, void *_ud)
Definition diff3.hpp:321
diff_progress_cb_t cb
Definition diff3.hpp:316
A range of the difference source.
Definition diff3.hpp:30
diffpos_t end
Definition diff3.hpp:32
void set_start(diffpos_t p)
Definition diff3.hpp:37
bool contains(diffpos_t p) const
Definition diff3.hpp:36
void set_end(diffpos_t p)
Definition diff3.hpp:43
bool operator==(const diff_range_t &r) const
Definition diff3.hpp:61
int compare(const diff_range_t &r) const
Definition diff3.hpp:59
diff_range_t(diffpos_t s=0, diffpos_t e=0)
Definition diff3.hpp:33
void intersect(const diff_range_t &r)
Definition diff3.hpp:49
void clear()
Definition diff3.hpp:35
bool empty() const
Definition diff3.hpp:34
diffpos_t start
Definition diff3.hpp:31
bool operator!=(const diff_range_t &r) const
Definition diff3.hpp:62
A difference region.
Definition diff3.hpp:95
void clear()
Definition diff3.hpp:98
diff_degree_t diff_degree
Definition diff3.hpp:96
qstring dstr() const
bool is_useless() const
Definition diff3.hpp:99
diff_action_t action
Definition diff3.hpp:97
A difference result.
Definition diff3.hpp:287
diff_regions_t regions
Definition diff3.hpp:290
size_t size() const
Definition diff3.hpp:294
diff_source_t * src2
Definition diff3.hpp:289
bool empty() const
Definition diff3.hpp:295
qstrvec_t print_region(const diff_region_t &b, bool with_details=true) const
qstrvec_t print_diff_result(bool with_details=true) const
diff_source_t * src1
Definition diff3.hpp:288
size_t merge_diff_sources(merge_policy_t merge_policy, size_t i1=0, size_t i2=SIZE_MAX)
merge src1 and src2 into src1.
diff_result_t(diff_source_t *s1=nullptr, diff_source_t *s2=nullptr)
Definition diff3.hpp:291
Definition diff3.hpp:116
diffpos_t pos
Definition diff3.hpp:117
void reverse()
Definition diff3.hpp:455
void append(const qstring &v, size_t idx)
Definition diff3.hpp:454
qstring part
vector's items
Definition diff3.hpp:448
lcsdiff_res_part_t(lcsdiff_result_action_t _a)
Definition diff3.hpp:452
lcsdiff_result_action_t action
action for items, lcsdiff_result_action_t
Definition diff3.hpp:450
qstring x_part
previous content, only for TDLA_MOD
Definition diff3.hpp:449
difference result, stores vectors' items with action to be applied to construct Y from X
Definition diff3.hpp:434
T x_part
previous content, only for TDLA_MOD
Definition diff3.hpp:436
void append(const T &v, size_t idx)
Definition diff3.hpp:441
T part
vector's items
Definition diff3.hpp:435
void reverse()
Definition diff3.hpp:442
lcsdiff_res_part_t(lcsdiff_result_action_t _a)
Definition diff3.hpp:439
lcsdiff_result_action_t action
action for items, lcsdiff_result_action_t
Definition diff3.hpp:437
virtual void on_event(event_t ev,...)=0
strdiff_printer_t()
Definition diff3.hpp:712
virtual ~strdiff_printer_t()
Definition diff3.hpp:713
event_t
Definition diff3.hpp:700
@ del_chars
deleted chars from line X, TDLA_SUB
Definition diff3.hpp:708
@ add_chars
added chars to line from X, TDLA_ADD
Definition diff3.hpp:706
@ same_chars
the same chars, TDLA_EQ
Definition diff3.hpp:704
@ term_chars
end printing
Definition diff3.hpp:702
@ init_chars
start printing
Definition diff3.hpp:701
event_t
Definition diff3.hpp:606
@ del_line
line is removed from X, TDLA_SUB
Definition diff3.hpp:618
@ next_line
start to print next line
Definition diff3.hpp:611
@ add_line
line is added to X, TDLA_ADD
Definition diff3.hpp:616
@ mod_line
line is changed, TDLA_MOD
Definition diff3.hpp:620
@ init
start printing
Definition diff3.hpp:607
@ same_line
line is the same in X and Y, TDLA_EQ
Definition diff3.hpp:614
@ term
end printing
Definition diff3.hpp:608
txtdiff_printer_t()
Definition diff3.hpp:625
virtual ~txtdiff_printer_t()
Definition diff3.hpp:626
virtual void on_event(event_t ev,...)=0