17d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin//===-- DiffConsumer.h - Difference Consumer --------------------*- C++ -*-===// 27d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin// 37d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin// The LLVM Compiler Infrastructure 47d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin// 57d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin// This file is distributed under the University of Illinois Open Source 67d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin// License. See LICENSE.TXT for details. 77d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin// 87d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin//===----------------------------------------------------------------------===// 97d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin// 107d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin// This header defines the interface to the LLVM difference Consumer 117d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin// 127d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin//===----------------------------------------------------------------------===// 137d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 147d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin#ifndef _LLVM_DIFFCONSUMER_H_ 157d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin#define _LLVM_DIFFCONSUMER_H_ 167d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 177d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin#include "DiffLog.h" 187d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin#include "llvm/ADT/DenseMap.h" 19f010c464a11444733ec67e31aace8bcebeaf2588Chandler Carruth#include "llvm/ADT/SmallVector.h" 207d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin#include "llvm/ADT/StringRef.h" 217d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin#include "llvm/Support/Casting.h" 22f010c464a11444733ec67e31aace8bcebeaf2588Chandler Carruth#include "llvm/Support/raw_ostream.h" 237d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 247d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golinnamespace llvm { 257d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin class Module; 267d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin class Value; 277d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin class Function; 287d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 297d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin /// The interface for consumers of difference data. 30875c3ffcc992efd21e3a54bae36b1961ff0f8333Francois Pichet class Consumer { 312d24e2a396a1d211baaeedf32148a3b657240170David Blaikie virtual void anchor(); 32875c3ffcc992efd21e3a54bae36b1961ff0f8333Francois Pichet public: 337d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin /// Record that a local context has been entered. Left and 347d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin /// Right are IR "containers" of some sort which are being 357d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin /// considered for structural equivalence: global variables, 367d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin /// functions, blocks, instructions, etc. 377d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin virtual void enterContext(Value *Left, Value *Right) = 0; 387d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 397d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin /// Record that a local context has been exited. 407d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin virtual void exitContext() = 0; 417d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 427d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin /// Record a difference within the current context. 437d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin virtual void log(StringRef Text) = 0; 447d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 457d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin /// Record a formatted difference within the current context. 467d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin virtual void logf(const LogBuilder &Log) = 0; 477d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 487d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin /// Record a line-by-line instruction diff. 497d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin virtual void logd(const DiffLogBuilder &Log) = 0; 507d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 517d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin protected: 527d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin virtual ~Consumer() {} 537d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin }; 547d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 557d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin class DiffConsumer : public Consumer { 567d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin private: 577d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin struct DiffContext { 587d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin DiffContext(Value *L, Value *R) 597d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin : L(L), R(R), Differences(false), IsFunction(isa<Function>(L)) {} 607d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin Value *L; 617d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin Value *R; 627d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin bool Differences; 637d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin bool IsFunction; 647d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin DenseMap<Value*,unsigned> LNumbering; 657d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin DenseMap<Value*,unsigned> RNumbering; 667d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin }; 677d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 687d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin raw_ostream &out; 697d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin SmallVector<DiffContext, 5> contexts; 707d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin bool Differences; 717d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin unsigned Indent; 727d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 737d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin void printValue(Value *V, bool isL); 747d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin void header(); 757d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin void indent(); 767d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 777d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin public: 78a7542d5f870c5d98960d1676e23ac1d1d975d7e5Benjamin Kramer DiffConsumer() 79a7542d5f870c5d98960d1676e23ac1d1d975d7e5Benjamin Kramer : out(errs()), Differences(false), Indent(0) {} 807d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 817d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin bool hadDifferences() const; 8236b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines void enterContext(Value *L, Value *R) override; 8336b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines void exitContext() override; 8436b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines void log(StringRef text) override; 8536b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines void logf(const LogBuilder &Log) override; 8636b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines void logd(const DiffLogBuilder &Log) override; 877d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin }; 887d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin} 897d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin 907d4fc4fb345ee8a1de15c718a854b5f38c1e6e46Renato Golin#endif 91