[llvm-commits] [llvm] r43218 - in /llvm/trunk/docs/tutorial: LangImpl1.html LangImpl2.html index.html
Author: lattner Date: Mon Oct 22 01:34:15 2007 New Revision: 43218 URL: http://llvm.org/viewvc/llvm-project?rev=43218view=rev Log: Check in part 2: parser and ast. Added: llvm/trunk/docs/tutorial/LangImpl2.html Modified: llvm/trunk/docs/tutorial/LangImpl1.html llvm/trunk/docs/tutorial/index.html Modified: llvm/trunk/docs/tutorial/LangImpl1.html URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/tutorial/LangImpl1.html?rev=43218r1=43217r2=43218view=diff == --- llvm/trunk/docs/tutorial/LangImpl1.html (original) +++ llvm/trunk/docs/tutorial/LangImpl1.html Mon Oct 22 01:34:15 2007 @@ -56,7 +56,7 @@ pre # Compute the x'th fibonacci number. def fib(x) - if x 3 then + if x lt; 3 then 1 else fib(x-1)+fib(x-2) @@ -241,8 +241,8 @@ pWith this, we have the complete lexer for the basic Kaleidoscope language. Next we'll a href=LangImpl2.htmlbuild a simple parser that uses this to -build an Abstract Syntax Tree/a. If you prefer, you can jump to the a -href=index.htmlmain tutorial index page/a. +build an Abstract Syntax Tree/a. When we have that, we'll include a driver +so that you can use the lexer and parser together. /p /div Added: llvm/trunk/docs/tutorial/LangImpl2.html URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/tutorial/LangImpl2.html?rev=43218view=auto == --- llvm/trunk/docs/tutorial/LangImpl2.html (added) +++ llvm/trunk/docs/tutorial/LangImpl2.html Mon Oct 22 01:34:15 2007 @@ -0,0 +1,1177 @@ +!DOCTYPE HTML PUBLIC -//W3C//DTD HTML 4.01//EN + http://www.w3.org/TR/html4/strict.dtd; + +html +head + titleKaleidoscope: Implementing a Parser and AST/title + meta http-equiv=Content-Type content=text/html; charset=utf-8 + meta name=author content=Chris Lattner + link rel=stylesheet href=../llvm.css type=text/css +/head + +body + +div class=doc_titleKaleidoscope: Implementing a Parser and AST/div + +div class=doc_author + pWritten by a href=mailto:[EMAIL PROTECTED]Chris Lattner/a/p +/div + +!-- *** -- +div class=doc_sectiona name=introPart 2 Introduction/a/div +!-- *** -- + +div class=doc_text + +pWelcome to part 2 of the a href=index.htmlImplementing a language with +LLVM/a tutorial. This chapter shows you how to use the a +href=LangImpl1.htmlLexer built in Chapter 1/a to build a full a +href=http://en.wikipedia.org/wiki/Parsing;parser/a for +our Kaleidoscope language and build an a +href=http://en.wikipedia.org/wiki/Abstract_syntax_tree;Abstract Syntax +Tree/a (AST)./p + +pThe parser we will build uses a combination of a +href=http://en.wikipedia.org/wiki/Recursive_descent_parser;Recursive Descent +Parsing/a and a href= +http://en.wikipedia.org/wiki/Operator-precedence_parser;Operator-Precedence +Parsing/a to parse the Kaleidoscope language (the later for binary expression +and the former for everything else). Before we get to parsing though, lets talk +about the output of the parser: the Abstract Syntax Tree./p + +/div + +!-- *** -- +div class=doc_sectiona name=astThe Abstract Syntax Tree (AST)/a/div +!-- *** -- + +div class=doc_text + +pThe AST for a program captures its behavior in a way that it is easy for +later stages of the compiler (e.g. code generation) to interpret. We basically +want one object for each construct in the language, and the AST should closely +model the language. In Kaleidoscope, we have expressions, a prototype, and a +function object. We'll start with expressions first:/p + +div class=doc_code +pre +/// ExprAST - Base class for all expression nodes. +class ExprAST { +public: + virtual ~ExprAST() {} +}; + +/// NumberExprAST - Expression class for numeric literals like 1.0. +class NumberExprAST : public ExprAST { + double Val; +public: + NumberExprAST(double val) : Val(val) {} +}; +/pre +/div + +pThe code above shows the definition of the base ExprAST class and one +subclass which we use for numeric literals. The important thing about this is +that the NumberExprAST class captures the numeric value of the literal in the +class, so that later phases of the compiler can know what it is./p + +pRight now we only create the AST, so there are no useful accessor methods on +them. It would be very easy to add a virtual method to pretty print the code, +for example. Here are the other expression AST node definitions that we'll use +in the basic form of the Kaleidoscope language. +/p + +div class=doc_code +pre +/// VariableExprAST - Expression class for referencing a variable, like a. +class VariableExprAST : public ExprAST { + std::string Name; +public: +
[llvm-commits] [llvm] r43219 - in /llvm/trunk/docs/tutorial: JITTutorial1.html Tutorial1.tar.bz2 Tutorial1.zip
Author: resistor Date: Mon Oct 22 01:35:07 2007 New Revision: 43219 URL: http://llvm.org/viewvc/llvm-project?rev=43219view=rev Log: Add downloadable code samples. Added: llvm/trunk/docs/tutorial/Tutorial1.tar.bz2 (with props) llvm/trunk/docs/tutorial/Tutorial1.zip (with props) Modified: llvm/trunk/docs/tutorial/JITTutorial1.html Modified: llvm/trunk/docs/tutorial/JITTutorial1.html URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/tutorial/JITTutorial1.html?rev=43219r1=43218r2=43219view=diff == --- llvm/trunk/docs/tutorial/JITTutorial1.html (original) +++ llvm/trunk/docs/tutorial/JITTutorial1.html Mon Oct 22 01:35:07 2007 @@ -19,6 +19,18 @@ pWritten by a href=mailto:[EMAIL PROTECTED]Owen Anderson/a/p /div +!-- *** -- +div class=doc_sectiona name=introCode Samples/a/div +!-- *** -- + +div class=doc_text +All the code in this example can be downloaded at a href=Tutorial1.tar.bz2Tutorial1.tar.bz2/a or a href=Tutorial1.zipTutorial1.zip/a. +/div + +!-- *** -- +div class=doc_sectiona name=introA First Function/a/div +!-- *** -- + div class=doc_text pFor starters, lets consider a relatively straightforward function that takes three integer parameters and returns an arithmetic combination of them. This is nice and simple, especially since it involves no control flow:/p Added: llvm/trunk/docs/tutorial/Tutorial1.tar.bz2 URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/tutorial/Tutorial1.tar.bz2?rev=43219view=auto == Binary file - no diff available. Propchange: llvm/trunk/docs/tutorial/Tutorial1.tar.bz2 -- svn:mime-type = application/octet-stream Added: llvm/trunk/docs/tutorial/Tutorial1.zip URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/tutorial/Tutorial1.zip?rev=43219view=auto == Binary file - no diff available. Propchange: llvm/trunk/docs/tutorial/Tutorial1.zip -- svn:mime-type = application/octet-stream ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] [llvm] r43220 - /llvm/trunk/docs/tutorial/LangImpl2.html
Author: resistor Date: Mon Oct 22 01:48:28 2007 New Revision: 43220 URL: http://llvm.org/viewvc/llvm-project?rev=43220view=rev Log: Fix a few typos I noticed. Modified: llvm/trunk/docs/tutorial/LangImpl2.html Modified: llvm/trunk/docs/tutorial/LangImpl2.html URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/tutorial/LangImpl2.html?rev=43220r1=43219r2=43220view=diff == --- llvm/trunk/docs/tutorial/LangImpl2.html (original) +++ llvm/trunk/docs/tutorial/LangImpl2.html Mon Oct 22 01:48:28 2007 @@ -118,7 +118,7 @@ precedence of binary operators, lexical structure etc./p pFor our basic language, these are all of the expression nodes we'll define. -because it doesn't have conditional control flow, it isn't turing complete: +Because it doesn't have conditional control flow, it isn't Turing-complete; we'll fix that in a later installment. The two things we need next are a way to talk about the interface to a function, and a way to talk about functions themselves:/p @@ -195,9 +195,7 @@ our lexer will assume that CurTok is the current token that needs to be parsed./p -pAgain, we define -these with global variables: it would be better design to wrap the entire parser -in a class and use instance variables for these. +pAgain, we define these with global variables; it would be better design to wrap the entire parser in a class and use instance variables for these. /p div class=doc_code @@ -282,7 +280,7 @@ return null on an error./p pAnother interesting aspect of this function is that it uses recursion by -calling ttParseExpression/tt (we will soon see that ParseExpression can call +calling ttParseExpression/tt (we will soon see that ttParseExpression/tt can call ttParseParenExpr/tt). This is powerful because it allows us to handle recursive grammars, and keeps each production very simple. Note that parenthesis do not cause construction of AST nodes themselves. While we could @@ -716,7 +714,7 @@ /div pThe most interesting part of this is that we ignore top-level semi colons. -Why is this do you ask? The basic reason is that if you type 4 + 5 at the +Why is this, you ask? The basic reason is that if you type 4 + 5 at the command line, the parser doesn't know that that is the end of what you will type. For example, on the next line you could type def foo... in which case 4+5 is the end of a top-level expression. Alternatively you could type * 6, ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] [llvm] r43221 - in /llvm/trunk/docs/tutorial: LangImpl3.html index.html
Author: lattner Date: Mon Oct 22 02:01:42 2007 New Revision: 43221 URL: http://llvm.org/viewvc/llvm-project?rev=43221view=rev Log: start of chapter 3 Added: llvm/trunk/docs/tutorial/LangImpl3.html Modified: llvm/trunk/docs/tutorial/index.html Added: llvm/trunk/docs/tutorial/LangImpl3.html URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/tutorial/LangImpl3.html?rev=43221view=auto == --- llvm/trunk/docs/tutorial/LangImpl3.html (added) +++ llvm/trunk/docs/tutorial/LangImpl3.html Mon Oct 22 02:01:42 2007 @@ -0,0 +1,787 @@ +!DOCTYPE HTML PUBLIC -//W3C//DTD HTML 4.01//EN + http://www.w3.org/TR/html4/strict.dtd; + +html +head + titleKaleidoscope: Implementing code generation to LLVM IR/title + meta http-equiv=Content-Type content=text/html; charset=utf-8 + meta name=author content=Chris Lattner + link rel=stylesheet href=../llvm.css type=text/css +/head + +body + +div class=doc_titleKaleidoscope: Code generation to LLVM IR/div + +div class=doc_author + pWritten by a href=mailto:[EMAIL PROTECTED]Chris Lattner/a/p +/div + +!-- *** -- +div class=doc_sectiona name=introPart 3 Introduction/a/div +!-- *** -- + +div class=doc_text + +pWelcome to part 3 of the a href=index.htmlImplementing a language with +LLVM/a tutorial. This chapter shows you how to transform the a +href=LangImpl2.htmlAbstract Syntax Tree built in Chapter 2/a into LLVM IR. +This will teach you a little bit about how LLVM does things, as well as +demonstrate how easy it is to use. It's much more work to build a lexer and +parser than it is to generate LLVM IR code. +/p + +/div + +!-- *** -- +div class=doc_sectiona name=basicsCode Generation setup/a/div +!-- *** -- + +div class=doc_text + +p +In order to generate LLVM IR, we want some simple setup to get started. First, +we define virtual codegen methods in each AST class:/p + +div class=doc_code +pre +/// ExprAST - Base class for all expression nodes. +class ExprAST { +public: + virtual ~ExprAST() {} + virtual Value *Codegen() = 0; +}; + +/// NumberExprAST - Expression class for numeric literals like 1.0. +class NumberExprAST : public ExprAST { + double Val; +public: + NumberExprAST(double val) : Val(val) {} + virtual Value *Codegen(); +}; +... +/pre +/div + +pValue is the class used to represent a register in LLVM. The Codegen() +method says to emit IR for that AST node and all things it depends on. The +second thing we want is an Error method like we used for parser, which will +be used to report errors found during code generation (for example, use of an +undeclared parameter):/p + +div class=doc_code +pre +Value *ErrorV(const char *Str) { Error(Str); return 0; } + +static Module *TheModule; +static LLVMBuilder Builder; +static std::maplt;std::string, Value*gt; NamedValues; +/pre +/div + +pThe static variables will be used during code generation. ttTheModule/tt +is the LLVM construct that contains all of the functions and global variables in +a chunk of code. In many ways, it is the top-level structure that the LLVM IR +uses to contain code./p + +pThe ttBuilder/tt object is a helper object that makes it easy to generate +LLVM instructions. The ttBuilder/tt keeps track of the current place to +insert instructions and has methods to create new instructions./p + +pThe ttNamedValues/tt map keeps track of which values are defined in the +current scope and what their LLVM representation is. In this form of +Kaleidoscope, the only things that can be referenced are function parameters. +As such, function parameters will be in this map when generating code for their +function body./p + +p +With these basics in place, we can start talking about how to generate code for +each expression. Note that this assumes that the ttBuilder/tt has been set +up to generate code eminto/em something. For now, we'll assume that this +has already been done, and we'll just use it to emit code. +/p + +/div + +!-- *** -- +div class=doc_sectiona name=exprsExpression Code Generation/a/div +!-- *** -- + +div class=doc_text + +pGenerating LLVM code for expression nodes is very straight-forward: less +than 45 lines of commented code for all four of our expression nodes. First, +we'll do numeric literals:/p + +div class=doc_code +pre +Value *NumberExprAST::Codegen() { + return ConstantFP::get(Type::DoubleTy, APFloat(Val)); +} +/pre +/div + +pIn the LLVM IR, numeric constants are represented with the ConstantFP class, +which holds the numeric value in an APFloat internally (APFloat has
Re: [llvm-commits] [llvm] r43171 - /llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp
Hi Chris, Assuming an expansion from i64 to 2x i32, the code above will work for sextinreg amounts between 1 and 32. For greater amounts, the top part should get a sextinreg, and the bottom part should or togther the top and bottom shifted parts, similar to a expanded shift. not sure why you need to do something complicated for the bottom part. Consider sextinreg from i63 to i64. The operand expands to 2 x i32: Lo and Hi. It seems to me that nothing needs to be done to Lo, while Hi needs to undergo an sextinreg from i31 to i32. Ciao, Duncan. ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
Re: [llvm-commits] [llvm] r43191 - in /llvm/trunk: lib/CodeGen/BranchFolding.cpp test/CFrontend/2007-10-15-VoidPtr.c test/Transforms/BranchFolding/ test/Transforms/BranchFolding/2007-10-19-InlineAsmDi
On Oct 20, 2007, at 11:49 AM, Dale Johannesen wrote: On Oct 20, 2007, at 10:29 AM, Chris Lattner wrote: This is just a really ugly compatibility hack. Apparently GCC doesn't do cross jumping of inline asm statements as much as we do, and we've hit a significant body of code that depends on this not happening. The code in question is clearly broken, but at this point, I think it's important for LLVM to be bug compatible with GCC if it doesn't cost much. In this case, we only lose tail merging of inline asm statements, which impacts code size but not performance. Bill's change is not clearly the wrong thing. People using asm's are generally trying to do something they can't do more straightforwardly; they know what code they want the compiler to produce, and regard writing asm's as an exercise in coercing the compiler into producing it. (They should be writing in assembler IMO, but gcc decided years ago to support asm, and we're all stuck with it now.) Before moving to llvm, I was maintaining gcc for some time; I never had anybody complain their asm's were not optimized enough, and I got many complaints that asm's were optimized too much. I'm sympathetic to that viewpoint, but it can't be made to work. In this particular case, the user is using pairs of asms and expecting them to come out in the .s file in the same order as they wrote. There is no way the compiler can reasonably guarantee this to work: it would prevent all block reordering and control flow optimizations etc. Turning off tail merging happens to fix the cases that are failing, but it's just a band-aid, not a solution. -Chris ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] [llvm] r43222 - /llvm/trunk/docs/tutorial/LangImpl2.html
Author: lattner Date: Mon Oct 22 11:44:31 2007 New Revision: 43222 URL: http://llvm.org/viewvc/llvm-project?rev=43222view=rev Log: fit in 80 cols :) Modified: llvm/trunk/docs/tutorial/LangImpl2.html Modified: llvm/trunk/docs/tutorial/LangImpl2.html URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/tutorial/LangImpl2.html?rev=43222r1=43221r2=43222view=diff == --- llvm/trunk/docs/tutorial/LangImpl2.html (original) +++ llvm/trunk/docs/tutorial/LangImpl2.html Mon Oct 22 11:44:31 2007 @@ -195,7 +195,8 @@ our lexer will assume that CurTok is the current token that needs to be parsed./p -pAgain, we define these with global variables; it would be better design to wrap the entire parser in a class and use instance variables for these. +pAgain, we define these with global variables; it would be better design to +wrap the entire parser in a class and use instance variables for these. /p div class=doc_code ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
Re: [llvm-commits] [llvm] r43171 - /llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp
On Oct 21, 2007, at 10:34 AM, Duncan Sands wrote: Hi Chris, Assuming an expansion from i64 to 2x i32, the code above will work for sextinreg amounts between 1 and 32. For greater amounts, the top part should get a sextinreg, and the bottom part should or togther the top and bottom shifted parts, similar to a expanded shift. not sure why you need to do something complicated for the bottom part. Consider sextinreg from i63 to i64. The operand expands to 2 x i32: Lo and Hi. It seems to me that nothing needs to be done to Lo, while Hi needs to undergo an sextinreg from i31 to i32. Ah, you're right! -Chris ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
Re: [llvm-commits] [llvm] r43191 - in /llvm/trunk: lib/CodeGen/BranchFolding.cpp test/CFrontend/2007-10-15-VoidPtr.c test/Transforms/BranchFolding/ test/Transforms/BranchFolding/2007-10-19-InlineAsmDi
On Oct 22, 2007, at 9:35 AM, Chris Lattner wrote: On Oct 20, 2007, at 11:49 AM, Dale Johannesen wrote: On Oct 20, 2007, at 10:29 AM, Chris Lattner wrote: This is just a really ugly compatibility hack. Apparently GCC doesn't do cross jumping of inline asm statements as much as we do, and we've hit a significant body of code that depends on this not happening. The code in question is clearly broken, but at this point, I think it's important for LLVM to be bug compatible with GCC if it doesn't cost much. In this case, we only lose tail merging of inline asm statements, which impacts code size but not performance. Bill's change is not clearly the wrong thing. People using asm's are generally trying to do something they can't do more straightforwardly; they know what code they want the compiler to produce, and regard writing asm's as an exercise in coercing the compiler into producing it. (They should be writing in assembler IMO, but gcc decided years ago to support asm, and we're all stuck with it now.) Before moving to llvm, I was maintaining gcc for some time; I never had anybody complain their asm's were not optimized enough, and I got many complaints that asm's were optimized too much. I'm sympathetic to that viewpoint, but it can't be made to work. In this particular case, the user is using pairs of asms and expecting them to come out in the .s file in the same order as they wrote. There is no way the compiler can reasonably guarantee this to work: it would prevent all block reordering and control flow optimizations etc. Yeah, turning all that off is a bit much. (I did, however, get the question how do I prevent the compiler from rearranging my code more than once from the asm users. The current answer is you don't, but this is something that certain people want.) ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] [llvm] r43223 - /llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp
Author: baldrick Date: Mon Oct 22 13:26:21 2007 New Revision: 43223 URL: http://llvm.org/viewvc/llvm-project?rev=43223view=rev Log: Fix up the logic for result expanding the various extension operations so they work right for integers with funky bit-widths. For example, consider extending i48 to i64 on a 32 bit machine. The i64 result is expanded to 2 x i32. We know that the i48 operand will be promoted to i64, then also expanded to 2 x i32. If we had the expanded promoted operand to hand, then expanding the result would be trivial. Unfortunately at this stage we can only get hold of the promoted operand. So instead we kind of hand-expand, doing explicit shifting and truncating to get the top and bottom halves of the i64 operand into 2 x i32, which are then used to expand the result. This is harmless, because when the promoted operand is finally expanded all this bit fiddling turns into trivial operations which are eliminated either by the expansion code itself or the DAG combiner. Modified: llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp Modified: llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp?rev=43223r1=43222r2=43223view=diff == --- llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp (original) +++ llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp Mon Oct 22 13:26:21 2007 @@ -133,7 +133,8 @@ // Common routines. SDOperand CreateStackStoreLoad(SDOperand Op, MVT::ValueType DestVT); SDOperand HandleMemIntrinsic(SDNode *N); - + void SplitOp(SDOperand Op, SDOperand Lo, SDOperand Hi); + // Result Promotion. void PromoteResult(SDNode *N, unsigned ResNo); SDOperand PromoteResult_UNDEF(SDNode *N); @@ -498,6 +499,20 @@ return DAG.UpdateNodeOperands(SDOperand(N, 0), Ops, 6); } +/// SplitOp - Return the lower and upper halves of Op's bits in a value type +/// half the size of Op's. +void DAGTypeLegalizer::SplitOp(SDOperand Op, SDOperand Lo, SDOperand Hi) { + unsigned NVTBits = MVT::getSizeInBits(Op.getValueType())/2; + assert(MVT::getSizeInBits(Op.getValueType()) == 2*NVTBits + Cannot split odd sized integer type); + MVT::ValueType NVT = MVT::getIntegerType(NVTBits); + Lo = DAG.getNode(ISD::TRUNCATE, NVT, Op); + Hi = DAG.getNode(ISD::SRL, Op.getValueType(), Op, + DAG.getConstant(NVTBits, TLI.getShiftAmountTy())); + Hi = DAG.getNode(ISD::TRUNCATE, NVT, Hi); +} + + //===--===// // Result Promotion //===--===// @@ -805,33 +820,77 @@ Hi = N-getOperand(1); } -void DAGTypeLegalizer::ExpandResult_ANY_EXTEND(SDNode *N, +void DAGTypeLegalizer::ExpandResult_ANY_EXTEND(SDNode *N, SDOperand Lo, SDOperand Hi) { - MVT::ValueType NVT = TLI.getTypeToTransformTo(N-getValueType(0)); - // The low part is any extension of the input (which degenerates to a copy). - Lo = DAG.getNode(ISD::ANY_EXTEND, NVT, N-getOperand(0)); - Hi = DAG.getNode(ISD::UNDEF, NVT); // The high part is undefined. + SDOperand Op = N-getOperand(0); + if (MVT::getSizeInBits(Op.getValueType()) = MVT::getSizeInBits(NVT)) { +// The low part is any extension of the input (which degenerates to a copy). +Lo = DAG.getNode(ISD::ANY_EXTEND, NVT, Op); +Hi = DAG.getNode(ISD::UNDEF, NVT); // The high part is undefined. + } else { +// For example, extension of an i48 to an i64. The operand type necessarily +// promotes to the result type, so will end up being expanded too. +assert(getTypeAction(Op.getValueType()) == Promote + Don't know how to expand this result!); +SDOperand Res = GetPromotedOp(Op); +assert(Res.getValueType() == N-getValueType(0) + Operand over promoted?); +// Split the promoted operand. This will simplify when it is expanded. +SplitOp(Res, Lo, Hi); + } } void DAGTypeLegalizer::ExpandResult_ZERO_EXTEND(SDNode *N, SDOperand Lo, SDOperand Hi) { MVT::ValueType NVT = TLI.getTypeToTransformTo(N-getValueType(0)); - // The low part is zero extension of the input (which degenerates to a copy). - Lo = DAG.getNode(ISD::ZERO_EXTEND, NVT, N-getOperand(0)); - Hi = DAG.getConstant(0, NVT); // The high part is just a zero. + SDOperand Op = N-getOperand(0); + if (MVT::getSizeInBits(Op.getValueType()) = MVT::getSizeInBits(NVT)) { +// The low part is zero extension of the input (which degenerates to a copy). +Lo = DAG.getNode(ISD::ZERO_EXTEND, NVT, N-getOperand(0)); +Hi = DAG.getConstant(0, NVT); // The high part is just a zero. + } else { +// For example, extension of an i48 to an i64. The operand type necessarily +// promotes to the result
[llvm-commits] [llvm] r43225 - /llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp
Author: baldrick Date: Mon Oct 22 14:00:05 2007 New Revision: 43225 URL: http://llvm.org/viewvc/llvm-project?rev=43225view=rev Log: Support for expanding extending loads of integers with funky bit-widths. Modified: llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp Modified: llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp?rev=43225r1=43224r2=43225view=diff == --- llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp (original) +++ llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAGTypes.cpp Mon Oct 22 14:00:05 2007 @@ -935,17 +935,19 @@ int SVOffset = N-getSrcValueOffset(); unsigned Alignment = N-getAlignment(); bool isVolatile = N-isVolatile(); - + + assert(!(MVT::getSizeInBits(NVT) 7) Expanded type not byte sized!); + if (ExtType == ISD::NON_EXTLOAD) { Lo = DAG.getLoad(NVT, Ch, Ptr, N-getSrcValue(), SVOffset, isVolatile, Alignment); // Increment the pointer to the other half. -unsigned IncrementSize = MVT::getSizeInBits(Lo.getValueType())/8; +unsigned IncrementSize = MVT::getSizeInBits(NVT)/8; Ptr = DAG.getNode(ISD::ADD, Ptr.getValueType(), Ptr, getIntPtrConstant(IncrementSize)); Hi = DAG.getLoad(NVT, Ch, Ptr, N-getSrcValue(), SVOffset+IncrementSize, isVolatile, std::max(Alignment, IncrementSize)); - + // Build a factor node to remember that this load is independent of the // other one. Ch = DAG.getNode(ISD::TokenFactor, MVT::Other, Lo.getValue(1), @@ -954,19 +956,15 @@ // Handle endianness of the load. if (!TLI.isLittleEndian()) std::swap(Lo, Hi); - } else { + } else if (MVT::getSizeInBits(N-getLoadedVT()) = MVT::getSizeInBits(NVT)) { MVT::ValueType EVT = N-getLoadedVT(); - -if (EVT == NVT) - Lo = DAG.getLoad(NVT, Ch, Ptr, N-getSrcValue(), - SVOffset, isVolatile, Alignment); -else - Lo = DAG.getExtLoad(ExtType, NVT, Ch, Ptr, N-getSrcValue(), - SVOffset, EVT, isVolatile, - Alignment); + +Lo = DAG.getExtLoad(ExtType, NVT, Ch, Ptr, N-getSrcValue(), SVOffset, EVT, +isVolatile, Alignment); + // Remember the chain. Ch = Lo.getValue(1); - + if (ExtType == ISD::SEXTLOAD) { // The high part is obtained by SRA'ing all but one of the bits of the // lo part. @@ -981,13 +979,70 @@ // The high part is undefined. Hi = DAG.getNode(ISD::UNDEF, NVT); } + } else if (TLI.isLittleEndian()) { +// Little-endian - low bits are at low addresses. +Lo = DAG.getLoad(NVT, Ch, Ptr, N-getSrcValue(), SVOffset, + isVolatile, Alignment); + +unsigned ExcessBits = + MVT::getSizeInBits(N-getLoadedVT()) - MVT::getSizeInBits(NVT); +MVT::ValueType NEVT = MVT::getIntegerType(ExcessBits); + +// Increment the pointer to the other half. +unsigned IncrementSize = MVT::getSizeInBits(NVT)/8; +Ptr = DAG.getNode(ISD::ADD, Ptr.getValueType(), Ptr, + getIntPtrConstant(IncrementSize)); +Hi = DAG.getExtLoad(ExtType, NVT, Ch, Ptr, N-getSrcValue(), +SVOffset+IncrementSize, NEVT, +isVolatile, std::max(Alignment, IncrementSize)); + +// Build a factor node to remember that this load is independent of the +// other one. +Ch = DAG.getNode(ISD::TokenFactor, MVT::Other, Lo.getValue(1), + Hi.getValue(1)); + } else { +// Big-endian - high bits are at low addresses. Favor aligned loads at +// the cost of some bit-fiddling. +MVT::ValueType EVT = N-getLoadedVT(); +unsigned EBytes = (MVT::getSizeInBits(EVT) + 7)/8; +unsigned IncrementSize = MVT::getSizeInBits(NVT)/8; +unsigned ExcessBits = (EBytes - IncrementSize)*8; + +// Load both the high bits and maybe some of the low bits. +Hi = DAG.getExtLoad(ExtType, NVT, Ch, Ptr, N-getSrcValue(), SVOffset, + MVT::getIntegerType(MVT::getSizeInBits(EVT)-ExcessBits), +isVolatile, Alignment); + +// Increment the pointer to the other half. +Ptr = DAG.getNode(ISD::ADD, Ptr.getValueType(), Ptr, + getIntPtrConstant(IncrementSize)); +// Load the rest of the low bits. +Lo = DAG.getExtLoad(ISD::ZEXTLOAD, NVT, Ch, Ptr, N-getSrcValue(), +SVOffset+IncrementSize, MVT::getIntegerType(ExcessBits), +isVolatile, std::max(Alignment, IncrementSize)); + +// Build a factor node to remember that this load is independent of the +// other one. +Ch = DAG.getNode(ISD::TokenFactor, MVT::Other, Lo.getValue(1), + Hi.getValue(1)); + +if (ExcessBits MVT::getSizeInBits(NVT)) { + //
[llvm-commits] [llvm] r43226 - /llvm/trunk/tools/llvmc/llvmc.cpp
Author: lattner Date: Mon Oct 22 14:41:46 2007 New Revision: 43226 URL: http://llvm.org/viewvc/llvm-project?rev=43226view=rev Log: add a 'don't use me' marker. Modified: llvm/trunk/tools/llvmc/llvmc.cpp Modified: llvm/trunk/tools/llvmc/llvmc.cpp URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/llvmc/llvmc.cpp?rev=43226r1=43225r2=43226view=diff == --- llvm/trunk/tools/llvmc/llvmc.cpp (original) +++ llvm/trunk/tools/llvmc/llvmc.cpp Mon Oct 22 14:41:46 2007 @@ -253,6 +253,9 @@ // Make sure we print stack trace if we get bad signals sys::PrintStackTraceOnErrorSignal(); + std::cout NOTE: llvmc is highly experimental and mostly useless right + now.\nPlease use llvm-gcc directly instead.\n\n; + try { // Parse the command line options ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] [llvm] r43227 - /llvm/trunk/lib/CodeGen/RegAllocLocal.cpp
Author: evancheng Date: Mon Oct 22 14:42:28 2007 New Revision: 43227 URL: http://llvm.org/viewvc/llvm-project?rev=43227view=rev Log: Add missing paratheses. Modified: llvm/trunk/lib/CodeGen/RegAllocLocal.cpp Modified: llvm/trunk/lib/CodeGen/RegAllocLocal.cpp URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/RegAllocLocal.cpp?rev=43227r1=43226r2=43227view=diff == --- llvm/trunk/lib/CodeGen/RegAllocLocal.cpp (original) +++ llvm/trunk/lib/CodeGen/RegAllocLocal.cpp Mon Oct 22 14:42:28 2007 @@ -618,7 +618,7 @@ // Unallocatable register dead, ignore. continue; } else { -assert(!PhysRegsUsed[PhysReg] || PhysRegsUsed[PhysReg] == -1 +assert((!PhysRegsUsed[PhysReg] || PhysRegsUsed[PhysReg] == -1) Silently clearing a virtual register?); } ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] [llvm] r43228 - in /llvm/trunk: lib/Target/PowerPC/PPCISelLowering.cpp test/CodeGen/PowerPC/2007-10-21-LocalRegAllocAssert.ll
Author: evancheng Date: Mon Oct 22 14:46:19 2007 New Revision: 43228 URL: http://llvm.org/viewvc/llvm-project?rev=43228view=rev Log: Use ptr type in the immediate field of a BxA instruction so we don't end up selecting 32-bit call instruction for ppc64. Added: llvm/trunk/test/CodeGen/PowerPC/2007-10-21-LocalRegAllocAssert.ll Modified: llvm/trunk/lib/Target/PowerPC/PPCISelLowering.cpp Modified: llvm/trunk/lib/Target/PowerPC/PPCISelLowering.cpp URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/PowerPC/PPCISelLowering.cpp?rev=43228r1=43227r2=43228view=diff == --- llvm/trunk/lib/Target/PowerPC/PPCISelLowering.cpp (original) +++ llvm/trunk/lib/Target/PowerPC/PPCISelLowering.cpp Mon Oct 22 14:46:19 2007 @@ -1537,7 +1537,8 @@ (Addr 6 6) != Addr) return 0; // Top 6 bits have to be sext of immediate. - return DAG.getConstant((int)C-getValue() 2, MVT::i32).Val; + return DAG.getConstant((int)C-getValue() 2, + DAG.getTargetLoweringInfo().getPointerTy()).Val; } Added: llvm/trunk/test/CodeGen/PowerPC/2007-10-21-LocalRegAllocAssert.ll URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/CodeGen/PowerPC/2007-10-21-LocalRegAllocAssert.ll?rev=43228view=auto == --- llvm/trunk/test/CodeGen/PowerPC/2007-10-21-LocalRegAllocAssert.ll (added) +++ llvm/trunk/test/CodeGen/PowerPC/2007-10-21-LocalRegAllocAssert.ll Mon Oct 22 14:46:19 2007 @@ -0,0 +1,27 @@ +; RUN: llvm-as %s | llc -mtriple=powerpc64-apple-darwin9 -regalloc=local -relocation-model=pic + + %struct.NSError = type opaque + %struct.NSManagedObjectContext = type opaque + %struct.NSPersistentStoreCoordinator = type opaque + %struct.NSString = type opaque + %struct.NSURL = type opaque + %struct._message_ref_t = type { %struct.objc_object* (%struct.objc_object*, %struct._message_ref_t*, ...)*, %struct.objc_selector* } + %struct.objc_object = type { } + %struct.objc_selector = type opaque +@\01L_OBJC_MESSAGE_REF_2 = external global %struct._message_ref_t ; %struct._message_ref_t* [#uses=1] +@\01L_OBJC_MESSAGE_REF_6 = external global %struct._message_ref_t ; %struct._message_ref_t* [#uses=1] [EMAIL PROTECTED] = external constant %struct.NSString* ; %struct.NSString** [#uses=1] +@\01L_OBJC_MESSAGE_REF_5 = external global %struct._message_ref_t ; %struct._message_ref_t* [#uses=2] +@\01L_OBJC_MESSAGE_REF_4 = external global %struct._message_ref_t ; %struct._message_ref_t* [#uses=1] + +define %struct.NSManagedObjectContext* @+[ListGenerator(Private) managedObjectContextWithModelURL:storeURL:](%struct.objc_object* %self, %struct._message_ref_t* %_cmd, %struct.NSURL* %modelURL, %struct.NSURL* %storeURL) { +entry: + %storeCoordinator = alloca %struct.NSPersistentStoreCoordinator* ; %struct.NSPersistentStoreCoordinator** [#uses=0] + %tmp29 = call %struct.objc_object* (%struct.objc_object*, %struct._message_ref_t*, ...)* null( %struct.objc_object* null, %struct._message_ref_t* @\01L_OBJC_MESSAGE_REF_2 ) ; %struct.objc_object* [#uses=0] + %tmp34 = load %struct.NSString** @NSXMLStoreType, align 8 ; %struct.NSString* [#uses=1] + %tmp37 = load %struct.objc_object* (%struct.objc_object*, %struct._message_ref_t*, ...)** getelementptr (%struct._message_ref_t* @\01L_OBJC_MESSAGE_REF_5, i32 0, i32 0), align 8 ; %struct.objc_object* (%struct.objc_object*, %struct._message_ref_t*, ...)* [#uses=1] + %tmp42 = call %struct.objc_object* (%struct.objc_object*, %struct._message_ref_t*, ...)* null( %struct.objc_object* null, %struct._message_ref_t* @\01L_OBJC_MESSAGE_REF_4, i32 1 ) ; %struct.objc_object* [#uses=1] + %tmp45 = call %struct.objc_object* (%struct.objc_object*, %struct._message_ref_t*, ...)* %tmp37( %struct.objc_object* null, %struct._message_ref_t* @\01L_OBJC_MESSAGE_REF_5, %struct.objc_object* %tmp42, %struct.NSString* null ) ; %struct.objc_object* [#uses=1] + %tmp48 = call %struct.objc_object* (%struct.objc_object*, %struct._message_ref_t*, ...)* null( %struct.objc_object* null, %struct._message_ref_t* @\01L_OBJC_MESSAGE_REF_6, %struct.NSString* %tmp34, i8* null, %struct.NSURL* null, %struct.objc_object* %tmp45, %struct.NSError** null ); %struct.objc_object* [#uses=0] + unreachable +} ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] [poolalloc] r43229 - /poolalloc/branches/SVA/lib/DSA/Local.cpp
Author: criswell Date: Mon Oct 22 14:57:26 2007 New Revision: 43229 URL: http://llvm.org/viewvc/llvm-project?rev=43229view=rev Log: Make DSA compile correctly in kernel and non-kernel mode. Modified: poolalloc/branches/SVA/lib/DSA/Local.cpp Modified: poolalloc/branches/SVA/lib/DSA/Local.cpp URL: http://llvm.org/viewvc/llvm-project/poolalloc/branches/SVA/lib/DSA/Local.cpp?rev=43229r1=43228r2=43229view=diff == --- poolalloc/branches/SVA/lib/DSA/Local.cpp (original) +++ poolalloc/branches/SVA/lib/DSA/Local.cpp Mon Oct 22 14:57:26 2007 @@ -1490,8 +1490,8 @@ N-setModifiedMarker()-setReadMarker(); return true; #endif - } #endif + } return false; } @@ -1553,12 +1553,14 @@ } } +#ifdef LLVA_KERNEL if (isSyscall6) { assert (isaConstantInt(CS.getArgument(0)) llva_syscall6 called with non-const argument); ConstantInt * C = dyn_castConstantInt(CS.getArgument(0)); Callee = syscalls[C-getSExtValue()]; assert (Callee llva_syscall: No target for system call vector); } +#endif // Set up the return value... DSNodeHandle RetVal; ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] [llvm] r43230 - in /llvm/trunk: lib/Target/X86/X86ISelDAGToDAG.cpp test/CodeGen/X86/fold-mul-lohi.ll
Author: djg Date: Mon Oct 22 15:22:24 2007 New Revision: 43230 URL: http://llvm.org/viewvc/llvm-project?rev=43230view=rev Log: Fix the folding of multiplication into addresses on x86, which was broken by the recent {U,S}MUL_LOHI changes. Added: llvm/trunk/test/CodeGen/X86/fold-mul-lohi.ll Modified: llvm/trunk/lib/Target/X86/X86ISelDAGToDAG.cpp Modified: llvm/trunk/lib/Target/X86/X86ISelDAGToDAG.cpp URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/X86/X86ISelDAGToDAG.cpp?rev=43230r1=43229r2=43230view=diff == --- llvm/trunk/lib/Target/X86/X86ISelDAGToDAG.cpp (original) +++ llvm/trunk/lib/Target/X86/X86ISelDAGToDAG.cpp Mon Oct 22 15:22:24 2007 @@ -681,6 +681,11 @@ } break; + case ISD::SMUL_LOHI: + case ISD::UMUL_LOHI: +// A mul_lohi where we need the low part can be folded as a plain multiply. +if (N.ResNo != 0) break; +// FALL THROUGH case ISD::MUL: // X*[3,5,9] - X+X*[2,4,8] if (!Available Added: llvm/trunk/test/CodeGen/X86/fold-mul-lohi.ll URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/CodeGen/X86/fold-mul-lohi.ll?rev=43230view=auto == --- llvm/trunk/test/CodeGen/X86/fold-mul-lohi.ll (added) +++ llvm/trunk/test/CodeGen/X86/fold-mul-lohi.ll Mon Oct 22 15:22:24 2007 @@ -0,0 +1,30 @@ +; RUN: llvm-as %s | llc -march=x86 | not grep lea +; RUN: llvm-as %s | llc -march=x86-64 | not grep lea + [EMAIL PROTECTED] = external global [1000 x i8], align 32 [EMAIL PROTECTED] = external global [1000 x i8], align 32 [EMAIL PROTECTED] = external global [1000 x i8], align 32 + +define void @foo(i32 %m) { +entry: + %tmp1 = icmp sgt i32 %m, 0 + br i1 %tmp1, label %bb, label %return + +bb: + %i.019.0 = phi i32 [ %indvar.next, %bb ], [ 0, %entry ] + %tmp2 = getelementptr [1000 x i8]* @B, i32 0, i32 %i.019.0 + %tmp3 = load i8* %tmp2, align 4 + %tmp4 = mul i8 %tmp3, 2 + %tmp5 = getelementptr [1000 x i8]* @A, i32 0, i32 %i.019.0 + store i8 %tmp4, i8* %tmp5, align 4 + %tmp8 = mul i32 %i.019.0, 9 + %tmp10 = getelementptr [1000 x i8]* @P, i32 0, i32 %tmp8 + store i8 17, i8* %tmp10, align 4 + %indvar.next = add i32 %i.019.0, 1 + %exitcond = icmp eq i32 %indvar.next, %m + br i1 %exitcond, label %return, label %bb + +return: + ret void +} + ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] [llvm] r43231 - in /llvm/trunk: lib/Transforms/Scalar/LoopStrengthReduce.cpp test/CodeGen/X86/2007-08-10-LEA16Use32.ll test/CodeGen/X86/stride-nine-with-base-reg.ll test/CodeGen/X86/str
Author: djg Date: Mon Oct 22 15:40:42 2007 New Revision: 43231 URL: http://llvm.org/viewvc/llvm-project?rev=43231view=rev Log: Strength reduction improvements. - Avoid attempting stride-reuse in the case that there are users that aren't addresses. In that case, there will be places where the multiplications won't be folded away, so it's better to try to strength-reduce them. - Several SSE intrinsics have operands that strength-reduction can treat as addresses. The previous item makes this more visible, as any non-address use of an IV can inhibit stride-reuse. - Make ValidStride aware of whether there's likely to be a base register in the address computation. This prevents it from thinking that things like stride 9 are valid on x86 when the base register is already occupied. Also, XFAIL the 2007-08-10-LEA16Use32.ll test; the new logic to avoid stride-reuse elimintes the LEA in the loop, so the test is no longer testing what it was intended to test. Added: llvm/trunk/test/CodeGen/X86/stride-nine-with-base-reg.ll llvm/trunk/test/CodeGen/X86/stride-reuse.ll Modified: llvm/trunk/lib/Transforms/Scalar/LoopStrengthReduce.cpp llvm/trunk/test/CodeGen/X86/2007-08-10-LEA16Use32.ll Modified: llvm/trunk/lib/Transforms/Scalar/LoopStrengthReduce.cpp URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Scalar/LoopStrengthReduce.cpp?rev=43231r1=43230r2=43231view=diff == --- llvm/trunk/lib/Transforms/Scalar/LoopStrengthReduce.cpp (original) +++ llvm/trunk/lib/Transforms/Scalar/LoopStrengthReduce.cpp Mon Oct 22 15:40:42 2007 @@ -175,10 +175,12 @@ bool FindIVForUser(ICmpInst *Cond, IVStrideUse *CondUse, const SCEVHandle *CondStride); -unsigned CheckForIVReuse(const SCEVHandle, IVExpr, const Type*, +unsigned CheckForIVReuse(bool, const SCEVHandle, + IVExpr, const Type*, const std::vectorBasedUser UsersToProcess); -bool ValidStride(int64_t, const std::vectorBasedUser UsersToProcess); +bool ValidStride(bool, int64_t, + const std::vectorBasedUser UsersToProcess); void StrengthReduceStridedIVUsers(const SCEVHandle Stride, IVUsersOfOneStride Uses, @@ -937,8 +939,8 @@ /// isZero - returns true if the scalar evolution expression is zero. /// -static bool isZero(SCEVHandle V) { - if (SCEVConstant *SC = dyn_castSCEVConstant(V)) +static bool isZero(const SCEVHandle V) { + if (const SCEVConstant *SC = dyn_castSCEVConstant(V)) return SC-getValue()-isZero(); return false; } @@ -946,7 +948,8 @@ /// ValidStride - Check whether the given Scale is valid for all loads and /// stores in UsersToProcess. /// -bool LoopStrengthReduce::ValidStride(int64_t Scale, +bool LoopStrengthReduce::ValidStride(bool HasBaseReg, + int64_t Scale, const std::vectorBasedUser UsersToProcess) { for (unsigned i=0, e = UsersToProcess.size(); i!=e; ++i) { // If this is a load or other access, pass the type of the access in. @@ -959,6 +962,7 @@ TargetLowering::AddrMode AM; if (SCEVConstant *SC = dyn_castSCEVConstant(UsersToProcess[i].Imm)) AM.BaseOffs = SC-getValue()-getSExtValue(); +AM.HasBaseReg = HasBaseReg || !isZero(UsersToProcess[i].Base); AM.Scale = Scale; // If load[imm+r*scale] is illegal, bail out. @@ -970,9 +974,11 @@ /// CheckForIVReuse - Returns the multiple if the stride is the multiple /// of a previous stride and it is a legal value for the target addressing -/// mode scale component. This allows the users of this stride to be rewritten -/// as prev iv * factor. It returns 0 if no reuse is possible. -unsigned LoopStrengthReduce::CheckForIVReuse(const SCEVHandle Stride, +/// mode scale component and optional base reg. This allows the users of +/// this stride to be rewritten as prev iv * factor. It returns 0 if no +/// reuse is possible. +unsigned LoopStrengthReduce::CheckForIVReuse(bool HasBaseReg, +const SCEVHandle Stride, IVExpr IV, const Type *Ty, const std::vectorBasedUser UsersToProcess) { if (!TLI) return 0; @@ -992,7 +998,7 @@ // stores; if it can be used for some and not others, we might as well use // the original stride everywhere, since we have to create the IV for it // anyway. - if (ValidStride(Scale, UsersToProcess)) + if (ValidStride(HasBaseReg, Scale, UsersToProcess)) for (std::vectorIVExpr::iterator II = SI-second.IVs.begin(), IE = SI-second.IVs.end(); II != IE; ++II) // FIXME: Only handle base == 0 for now. @@ -1061,7 +1067,18 @@ // UsersToProcess base values. SCEVHandle CommonExprs =
[llvm-commits] [llvm] r43232 - /llvm/trunk/lib/VMCore/ConstantFold.h
Author: djg Date: Mon Oct 22 15:44:10 2007 New Revision: 43232 URL: http://llvm.org/viewvc/llvm-project?rev=43232view=rev Log: The #include iterator isn't needed in this header. Modified: llvm/trunk/lib/VMCore/ConstantFold.h Modified: llvm/trunk/lib/VMCore/ConstantFold.h URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/VMCore/ConstantFold.h?rev=43232r1=43231r2=43232view=diff == --- llvm/trunk/lib/VMCore/ConstantFold.h (original) +++ llvm/trunk/lib/VMCore/ConstantFold.h Mon Oct 22 15:44:10 2007 @@ -19,8 +19,6 @@ #ifndef CONSTANTFOLDING_H #define CONSTANTFOLDING_H -#include iterator - namespace llvm { class Value; class Constant; @@ -48,7 +46,6 @@ Constant *ConstantFoldCompareInstruction(unsigned short predicate, const Constant *C1, const Constant *C2); - Constant *ConstantFoldGetElementPtr(const Constant *C, Constant* const *Idxs, unsigned NumIdx); } // End llvm namespace ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
Re: [llvm-commits] [llvm] r43176 - in /llvm/trunk/lib/Target/ARM: ARMISelLowering.cpp ARMISelLowering.h
Hi Rafael, There a couple of problems with this patch. 1. This breaks a number of tests for me: llc-beta /MultiSource/Applications/JM/ldecod/ldecod llc /MultiSource/Applications/JM/ldecod/ldecod llc /External/SPEC/CINT2000/254.gap/254.gap llc /MultiSource/Benchmarks/MiBench/office-ispell/office-ispell llc-beta /MultiSource/Benchmarks/MiBench/office-ispell/office-ispell llc-beta /External/SPEC/CINT2000/254.gap/254.gap LowerMEMCPYInline() is asserting when the memcpy is 4-byte aligned but the size isn't multiple of 4. I'm going to remove the assertion and issue byte / word loads / stores to handle the trailing bytes. Please let me know if that's undesirable. 2. The stores are unnecessarily serialized. Each of them should use the load tokenfactor as input chain. All the chains produced by the stores should then be fed into a new tokenfactor. I'll fix this. Thanks, Evan On Oct 19, 2007, at 7:35 AM, Rafael Espindola wrote: Author: rafael Date: Fri Oct 19 09:35:17 2007 New Revision: 43176 URL: http://llvm.org/viewvc/llvm-project?rev=43176view=rev Log: split LowerMEMCPY into LowerMEMCPYCall and LowerMEMCPYInline in the ARM backend. Modified: llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp llvm/trunk/lib/Target/ARM/ARMISelLowering.h Modified: llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp?rev=43176r1=43175r2=43176view=diff = = = = = = = = == --- llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp (original) +++ llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp Fri Oct 19 09:35:17 2007 @@ -1288,40 +1288,73 @@ } SDOperand ARMTargetLowering::LowerMEMCPY(SDOperand Op, SelectionDAG DAG) { - SDOperand Chain = Op.getOperand(0); - SDOperand Dest = Op.getOperand(1); - SDOperand Src = Op.getOperand(2); - SDOperand Count = Op.getOperand(3); - unsigned Align = -(unsigned)castConstantSDNode(Op.getOperand(4))-getValue(); + SDOperand ChainOp = Op.getOperand(0); + SDOperand DestOp = Op.getOperand(1); + SDOperand SourceOp = Op.getOperand(2); + SDOperand CountOp = Op.getOperand(3); + SDOperand AlignOp = Op.getOperand(4); + SDOperand AlwaysInlineOp = Op.getOperand(5); + + bool AlwaysInline = (bool)castConstantSDNode(AlwaysInlineOp)- getValue(); + unsigned Align = (unsigned)castConstantSDNode(AlignOp)- getValue(); if (Align == 0) Align = 1; - ConstantSDNode *I = dyn_castConstantSDNode(Count); - // Just call memcpy if: - // not 4-byte aligned - // size is unknown - // size is = the threshold. - if ((Align 3) != 0 || - !I || - I-getValue() = 64 || - (I-getValue() 3) != 0) { -MVT::ValueType IntPtr = getPointerTy(); -TargetLowering::ArgListTy Args; -TargetLowering::ArgListEntry Entry; -Entry.Ty = getTargetData()-getIntPtrType(); -Entry.Node = Op.getOperand(1); Args.push_back(Entry); -Entry.Node = Op.getOperand(2); Args.push_back(Entry); -Entry.Node = Op.getOperand(3); Args.push_back(Entry); -std::pairSDOperand,SDOperand CallResult = + // If size is unknown, call memcpy. + ConstantSDNode *I = dyn_castConstantSDNode(CountOp); + if (!I) { +assert(!AlwaysInline Cannot inline copy of unknown size); +return LowerMEMCPYCall(ChainOp, DestOp, SourceOp, CountOp, DAG); + } + unsigned Size = I-getValue(); + + if (AlwaysInline) +return LowerMEMCPYInline(ChainOp, DestOp, SourceOp, Size, Align, DAG); + + // The libc version is likely to be faster for the following cases. It can + // use the address value and run time information about the CPU. + // With glibc 2.6.1 on a core 2, coping an array of 100M longs was 30% faster + + // If not DWORD aligned, call memcpy. + if ((Align 3) != 0) +return LowerMEMCPYCall(ChainOp, DestOp, SourceOp, CountOp, DAG); + + // If size is more than the threshold, call memcpy. + // if (Size Subtarget-getMinRepStrSizeThreshold()) + if (Size = 64) +return LowerMEMCPYCall(ChainOp, DestOp, SourceOp, CountOp, DAG); + + return LowerMEMCPYInline(ChainOp, DestOp, SourceOp, Size, Align, DAG); +} + +SDOperand ARMTargetLowering::LowerMEMCPYCall(SDOperand Chain, + SDOperand Dest, + SDOperand Source, + SDOperand Count, + SelectionDAG DAG) { + MVT::ValueType IntPtr = getPointerTy(); + TargetLowering::ArgListTy Args; + TargetLowering::ArgListEntry Entry; + Entry.Ty = getTargetData()-getIntPtrType(); + Entry.Node = Dest; Args.push_back(Entry); + Entry.Node = Source; Args.push_back(Entry); + Entry.Node = Count; Args.push_back(Entry); + std::pairSDOperand,SDOperand CallResult = LowerCallTo(Chain, Type::VoidTy, false, false, CallingConv::C,
Re: [llvm-commits] [llvm] r43221 - in /llvm/trunk/docs/tutorial: LangImpl3.html index.html
Value is the class used to represent a register in LLVM. The Codegen() method says to emit IR for that AST It would be good to mention that the registers here cannot be reassigned, as the word register might seem to imply. I don't know much you want to say about SSA at this point in the tutorial, or if you want to go into using entry-block Allocas and mem2reg to avoid having to compute SSA in a front-end here, but it's something that should be mentioned somewhere. NumberExprAST(double val) : Val(val) {} VariableExprAST(const std::string name) : Name(name) {} These miss explicit keywords. case '+': return Builder.CreateAdd(L, R, addtmp); case '-': return Builder.CreateSub(L, R, subtmp); case '*': return Builder.CreateMul(L, R, multmp); You might mention that the names addtmp and so on are automatically make unique by LLVM in case there's more than one add in the program, for example. Dan -- Dan Gohman, Cray Inc. ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] [llvm] r43234 - in /llvm/trunk: lib/Target/ARM/ARMISelLowering.cpp lib/Target/ARM/ARMISelLowering.h lib/Target/ARM/README-Thumb.txt test/CodeGen/ARM/memcpy-inline.ll
Author: evancheng Date: Mon Oct 22 17:11:27 2007 New Revision: 43234 URL: http://llvm.org/viewvc/llvm-project?rev=43234view=rev Log: Fix memcpy lowering when addresses are 4-byte aligned but size is not multiple of 4. Added: llvm/trunk/test/CodeGen/ARM/memcpy-inline.ll Modified: llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp llvm/trunk/lib/Target/ARM/ARMISelLowering.h llvm/trunk/lib/Target/ARM/README-Thumb.txt Modified: llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp?rev=43234r1=43233r2=43234view=diff == --- llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp (original) +++ llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp Mon Oct 22 17:11:27 2007 @@ -1287,7 +1287,8 @@ return DAG.getNode(ISD::BUILD_PAIR, MVT::i64, Lo, Hi); } -SDOperand ARMTargetLowering::LowerMEMCPY(SDOperand Op, SelectionDAG DAG) { +SDOperand ARMTargetLowering::LowerMEMCPY(SDOperand Op, SelectionDAG DAG, + const ARMSubtarget *ST) { SDOperand ChainOp = Op.getOperand(0); SDOperand DestOp = Op.getOperand(1); SDOperand SourceOp = Op.getOperand(2); @@ -1305,25 +1306,18 @@ assert(!AlwaysInline Cannot inline copy of unknown size); return LowerMEMCPYCall(ChainOp, DestOp, SourceOp, CountOp, DAG); } - unsigned Size = I-getValue(); - - if (AlwaysInline) -return LowerMEMCPYInline(ChainOp, DestOp, SourceOp, Size, Align, DAG); - // The libc version is likely to be faster for the following cases. It can + // If not DWORD aligned or if size is more than threshold, then call memcpy. + // The libc version is likely to be faster for the these cases. It can // use the address value and run time information about the CPU. // With glibc 2.6.1 on a core 2, coping an array of 100M longs was 30% faster - - // If not DWORD aligned, call memcpy. - if ((Align 3) != 0) -return LowerMEMCPYCall(ChainOp, DestOp, SourceOp, CountOp, DAG); - - // If size is more than the threshold, call memcpy. - // if (Size Subtarget-getMinRepStrSizeThreshold()) - if (Size = 64) -return LowerMEMCPYCall(ChainOp, DestOp, SourceOp, CountOp, DAG); - - return LowerMEMCPYInline(ChainOp, DestOp, SourceOp, Size, Align, DAG); + // FIXME: For now, we don't lower memcpy's to loads / stores for Thumb. Change + // this once Thumb ldmia / stmia support is added. + unsigned Size = I-getValue(); + if (AlwaysInline || + (!ST-isThumb() Size 64 (Align 3) == 0)) +return LowerMEMCPYInline(ChainOp, DestOp, SourceOp, Size, Align, DAG); + return LowerMEMCPYCall(ChainOp, DestOp, SourceOp, CountOp, DAG); } SDOperand ARMTargetLowering::LowerMEMCPYCall(SDOperand Chain, @@ -1350,46 +1344,93 @@ unsigned Size, unsigned Align, SelectionDAG DAG) { - - // Do repeated 4-byte loads and stores. To be improved. - assert((Size 3) == 0); - assert((Align 3) == 0); + // Do repeated 4-byte loads and stores. To be improved. + assert((Align 3) == 0 Expected 4-byte aligned addresses!); + unsigned BytesLeft = Size 3; unsigned NumMemOps = Size 2; unsigned EmittedNumMemOps = 0; unsigned SrcOff = 0, DstOff = 0; MVT::ValueType VT = MVT::i32; unsigned VTSize = 4; + unsigned i = 0; const unsigned MAX_LOADS_IN_LDM = 6; - SDOperand LoadChains[MAX_LOADS_IN_LDM]; + SDOperand TFOps[MAX_LOADS_IN_LDM]; SDOperand Loads[MAX_LOADS_IN_LDM]; - // Emit up to 4 loads, then a TokenFactor barrier, then the same - // number of stores. The loads and stores will get combined into + // Emit up to MAX_LOADS_IN_LDM loads, then a TokenFactor barrier, then the + // same number of stores. The loads and stores will get combined into // ldm/stm later on. - while(EmittedNumMemOps NumMemOps) { -unsigned i; -for (i=0; iMAX_LOADS_IN_LDM EmittedNumMemOps+i NumMemOps; i++) { + while (EmittedNumMemOps NumMemOps) { +for (i = 0; + i MAX_LOADS_IN_LDM EmittedNumMemOps + i NumMemOps; ++i) { Loads[i] = DAG.getLoad(VT, Chain, - DAG.getNode(ISD::ADD, VT, Source, - DAG.getConstant(SrcOff, VT)), + DAG.getNode(ISD::ADD, MVT::i32, Source, + DAG.getConstant(SrcOff, MVT::i32)), NULL, 0); - LoadChains[i] = Loads[i].getValue(1); + TFOps[i] = Loads[i].getValue(1); SrcOff += VTSize; } +Chain = DAG.getNode(ISD::TokenFactor, MVT::Other, TFOps[0], i); -Chain = DAG.getNode(ISD::TokenFactor, MVT::Other, LoadChains[0], i); - -for (i=0; iMAX_LOADS_IN_LDM EmittedNumMemOps+i NumMemOps; i++) { - Chain = DAG.getStore(Chain, Loads[i], -
Re: [llvm-commits] [llvm] r43221 - in /llvm/trunk/docs/tutorial: LangImpl3.html index.html
Dan, I'm planning to cover both of those points in the Basic Topics sections of the tutorial. --Owen smime.p7s Description: S/MIME cryptographic signature ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
Re: [llvm-commits] [llvm] r43221 - in /llvm/trunk/docs/tutorial: LangImpl3.html index.html
Dan, I'm planning to cover both of those points in the Basic Topics sections of the tutorial. --Owen smime.p7s Description: S/MIME cryptographic signature ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] makeinfo versions for llvm-gcc
Hi, There's a problem with the makeinfo test in llvm-gcc where it checks for a makeinfo version = 4.4. It treats 4.10 as less than 4.4 The attached patch should be applied to both llvm-gcc4.0 and 4.2. Thanks, Nick ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] makeinfo versions for llvm-gcc
and this time with the attachment! Hi, There's a problem with the makeinfo test in llvm-gcc where it checks for a makeinfo version = 4.4. It treats 4.10 as less than 4.4 The attached patch should be applied to both llvm-gcc4.0 and 4.2. Thanks, Nick Index: configure.in === --- configure.in (revision 43047) +++ configure.in (working copy) @@ -2256,7 +2256,7 @@ # For an installed makeinfo, we require it to be from texinfo 4.4 or # higher, else we use the missing dummy. if ${MAKEINFO} --version \ - | egrep 'texinfo[^0-9]*([1-3][0-9]|4\.[4-9]|[5-9])' /dev/null 21; then + | egrep 'texinfo[^0-9]*([1-3][0-9]|4\.([4-9]|[1-9][0-9])|[5-9])' /dev/null 21; then : else MAKEINFO=$MISSING makeinfo ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
Re: [llvm-commits] [llvm] r43221 - in /llvm/trunk/docs/tutorial: LangImpl3.html index.html
On Oct 22, 2007, at 3:05 PM, Dan Gohman wrote: Value is the class used to represent a register in LLVM. The Codegen() method says to emit IR for that AST It would be good to mention that the registers here cannot be reassigned, as the word register might seem to imply. Good idea. I don't know much you want to say about SSA at this point in the tutorial, or if you want to go into using entry-block Allocas and mem2reg to avoid having to compute SSA in a front-end here, but it's something that should be mentioned somewhere. I plan to unveil it slowly: in the if/then/else chapter, I'll talk about phi nodes. In the mutable variables chapter, I'll talk about the alloca trick. NumberExprAST(double val) : Val(val) {} VariableExprAST(const std::string name) : Name(name) {} These miss explicit keywords. *grumble* explicit should be the default *grumble* :) case '+': return Builder.CreateAdd(L, R, addtmp); case '-': return Builder.CreateSub(L, R, subtmp); case '*': return Builder.CreateMul(L, R, multmp); You might mention that the names addtmp and so on are automatically make unique by LLVM in case there's more than one add in the program, for example. will do! -Chris ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] [llvm] r43238 - /llvm/trunk/docs/tutorial/LangImpl3.html
Author: lattner Date: Mon Oct 22 23:51:30 2007 New Revision: 43238 URL: http://llvm.org/viewvc/llvm-project?rev=43238view=rev Log: Finish up expr codegen. Modified: llvm/trunk/docs/tutorial/LangImpl3.html Modified: llvm/trunk/docs/tutorial/LangImpl3.html URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/tutorial/LangImpl3.html?rev=43238r1=43237r2=43238view=diff == --- llvm/trunk/docs/tutorial/LangImpl3.html (original) +++ llvm/trunk/docs/tutorial/LangImpl3.html Mon Oct 22 23:51:30 2007 @@ -132,12 +132,13 @@ /pre /div -pIn the LLVM IR, numeric constants are represented with the ConstantFP class, -which holds the numeric value in an APFloat internally (APFloat has the -capability of holding floating point constants of arbitrary precision). This -code basically just creates and returns a ConstantFP. Note that in the LLVM IR +pIn the LLVM IR, numeric constants are represented with the +ttConstantFP/tt class, which holds the numeric value in an ttAPFloat/tt +internally (ttAPFloat/tt has the capability of holding floating point +constants of emA/emrbitrary emP/emrecision). This code basically just +creates and returns a ttConstantFP/tt. Note that in the LLVM IR that constants are all uniqued together and shared. For this reason, the API -uses the foo::get(...) idiom instead of a create method or new foo./p +uses the foo::get(..) idiom instead of new foo(..) or foo::create(..)./p div class=doc_code pre @@ -149,9 +150,10 @@ /pre /div -pReferences to variables is also quite simple here. In our system, we assume -that the variable has already been emited somewhere and its value is available. -In practice, the only values in the NamedValues map will be arguments. This +pReferences to variables is also quite simple here. In the simple version +of Kaleidoscope, we assume that the variable has already been emited somewhere +and its value is available. In practice, the only values that can be in the +ttNamedValues/tt map are function arguments. This code simply checks to see that the specified name is in the map (if not, an unknown variable is being referenced) and returns the value for it./p @@ -176,7 +178,38 @@ /pre /div - +pBinary operators start to get more interesting. The basic idea here is that +we recursively emit code for the left-hand side of the expression, then the +right-hand side, then we compute the result of the binary expression. In this +code, we do a simple switch on the opcode to create the right LLVM instruction. +/p + +pIn this example, the LLVM builder class is starting to show its value. +Because it knows where to insert the newly created instruction, you just have to +specificy what instruction to create (e.g. with ttCreateAdd/tt), which +operands to use (ttL/tt and ttR/tt here) and optionally provide a name +for the generated instruction. One nice thing about LLVM is that the name is +just a hint: if there are multiple additions in a single function, the first +will be named addtmp and the second will be autorenamed by adding a suffix, +giving it a name like addtmp42. Local value names for instructions are purely +optional, but it makes it much easier to read the IR dumps./p + +pa href=../LangRef.html#instrefLLVM instructions/a are constrained to +have very strict type properties: for example, the Left and Right operators of +an a href=../LangRef.html#i_addadd instruction/a have to have the same +type, and that the result of the add matches the operands. Because all values +in Kaleidoscope are doubles, this makes for very simple code for add, sub and +mul./p + +pOn the other hand, LLVM specifies that the a +href=../LangRef.html#i_fcmpfcmp instruction/a always returns an 'i1' value +(a one bit integer). However, Kaleidoscope wants the value to be a 0.0 or 1.0 +value. In order to get these semantics, we combine the fcmp instruction with +a a href=../LangRef.html#i_uitofpuitofp instruction/a. This instruction +converts its input integer into a floating point value by treating the input +as an unsigned value. In contrast, if we used the a +href=../LangRef.html#i_sitofpsitofp instruction/a, the Kaleidoscope '' +operator would return 0.0 and -1.0, depending on the input value./p div class=doc_code pre @@ -201,7 +234,24 @@ /pre /div -h1 more todo/h1 +pCode generation for function calls is quite straight-forward with LLVM. The +code above first looks the name of the function up in the LLVM Module's symbol +table. Recall that the LLVM Module is the container that holds all of the +functions we are JIT'ing. By giving each function the same name as what the +user specifies, we can use the LLVM symbol table to resolve function names for +us./p + +pOnce we have the function to call, we recursively codegen each argument that +is to be passed in, and create an LLVM a href=../LangRef.html#i_callcall +instruction/a. Note that LLVM uses the native C calling
[llvm-commits] [llvm] r43237 - in /llvm/trunk/docs/tutorial: LangImpl2.html LangImpl3.html
Author: lattner Date: Mon Oct 22 23:27:44 2007 New Revision: 43237 URL: http://llvm.org/viewvc/llvm-project?rev=43237view=rev Log: several improvements suggested by Dan, thanks! Modified: llvm/trunk/docs/tutorial/LangImpl2.html llvm/trunk/docs/tutorial/LangImpl3.html Modified: llvm/trunk/docs/tutorial/LangImpl2.html URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/tutorial/LangImpl2.html?rev=43237r1=43236r2=43237view=diff == --- llvm/trunk/docs/tutorial/LangImpl2.html (original) +++ llvm/trunk/docs/tutorial/LangImpl2.html Mon Oct 22 23:27:44 2007 @@ -65,7 +65,7 @@ class NumberExprAST : public ExprAST { double Val; public: - NumberExprAST(double val) : Val(val) {} + explicit NumberExprAST(double val) : Val(val) {} }; /pre /div @@ -87,7 +87,7 @@ class VariableExprAST : public ExprAST { std::string Name; public: - VariableExprAST(const std::string amp;name) : Name(name) {} + explicit VariableExprAST(const std::string amp;name) : Name(name) {} }; /// BinaryExprAST - Expression class for a binary operator. @@ -850,14 +850,14 @@ class NumberExprAST : public ExprAST { double Val; public: - NumberExprAST(double val) : Val(val) {} + explicit NumberExprAST(double val) : Val(val) {} }; /// VariableExprAST - Expression class for referencing a variable, like a. class VariableExprAST : public ExprAST { std::string Name; public: - VariableExprAST(const std::string amp;name) : Name(name) {} + explicit VariableExprAST(const std::string amp;name) : Name(name) {} }; /// BinaryExprAST - Expression class for a binary operator. Modified: llvm/trunk/docs/tutorial/LangImpl3.html URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/tutorial/LangImpl3.html?rev=43237r1=43236r2=43237view=diff == --- llvm/trunk/docs/tutorial/LangImpl3.html (original) +++ llvm/trunk/docs/tutorial/LangImpl3.html Mon Oct 22 23:27:44 2007 @@ -56,15 +56,26 @@ class NumberExprAST : public ExprAST { double Val; public: - NumberExprAST(double val) : Val(val) {} + explicit NumberExprAST(double val) : Val(val) {} virtual Value *Codegen(); }; ... /pre /div -pValue is the class used to represent a register in LLVM. The Codegen() -method says to emit IR for that AST node and all things it depends on. The +pThe Codegen() method says to emit IR for that AST node and all things it +depends on, and they all return an LLVM Value object. +Value is the class used to represent a a +href=http://en.wikipedia.org/wiki/Static_single_assignment_form;Static Single +Assignment (SSA)/a register or SSA value in LLVM. The most distinct aspect +of SSA values is that their value is computed as the related instruction +executes, and it does not get a new value until (and if) the instruction +re-executes. In order words, there is no way to change an SSA value. For +more information, please read up on a +href=http://en.wikipedia.org/wiki/Static_single_assignment_form;Static Single +Assignment/a - the concepts are really quite natural once you grok them./p + +pThe second thing we want is an Error method like we used for parser, which will be used to report errors found during code generation (for example, use of an undeclared parameter):/p @@ -299,7 +310,7 @@ class NumberExprAST : public ExprAST { double Val; public: - NumberExprAST(double val) : Val(val) {} + explicit NumberExprAST(double val) : Val(val) {} virtual Value *Codegen(); }; @@ -307,7 +318,7 @@ class VariableExprAST : public ExprAST { std::string Name; public: - VariableExprAST(const std::string amp;name) : Name(name) {} + explicit VariableExprAST(const std::string amp;name) : Name(name) {} virtual Value *Codegen(); }; ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
[llvm-commits] [llvm] r43239 - /llvm/trunk/docs/tutorial/LangImpl2.html
Author: lattner Date: Tue Oct 23 00:43:01 2007 New Revision: 43239 URL: http://llvm.org/viewvc/llvm-project?rev=43239view=rev Log: Fix up a broken #include, move code to its own section, add conclusions. Modified: llvm/trunk/docs/tutorial/LangImpl2.html Modified: llvm/trunk/docs/tutorial/LangImpl2.html URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/tutorial/LangImpl2.html?rev=43239r1=43238r2=43239view=diff == --- llvm/trunk/docs/tutorial/LangImpl2.html (original) +++ llvm/trunk/docs/tutorial/LangImpl2.html Tue Oct 23 00:43:01 2007 @@ -753,20 +753,40 @@ /pre /div +pThere is a lot of room for extension here. You can define new AST nodes, +extend the language in many ways, etc. In the a href=LangImpl3.htmlnext +installment/a, we will describe how to generate LLVM IR from the AST./p + +/div + +!-- *** -- +div class=doc_sectiona name=codeFull Code Listing/a/div +!-- *** -- + +div class=doc_text + p -Here is the full code. Note that it is fully self-contained: you don't even -need LLVM for this. In the a href=LangImpl3.htmlnext installment/a, we -will describe how to generate LLVM IR from the AST./p +Here is the complete code listing for this and the previous chapter. +Note that it is fully self-contained: you don't need LLVM or any external +libraries at all for this (other than the C and C++ standard libraries of +course). To build this, just compile with:/p div class=doc_code pre -// To build this: -// g++ -g toy.cpp -// ./a.out + # Compile + g++ -g toy.cpp + # Run + ./a.out +/pre +/div +pHere is the code:/p + +div class=doc_code +pre #include lt;cstdiogt; #include lt;stringgt; -#include lt; +#include lt;mapgt; #include lt;vectorgt; //===--===// ___ llvm-commits mailing list llvm-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits