[LLVMdev] Global variable-length array

Gordon Henriksen gordonhenriksen at mac.com
Sat Apr 19 21:09:08 PDT 2008


On Apr 19, 2008, at 22:45, Talin wrote:

> Suppose I have a global variable which points to a constant,  
> variable length array.

This is somewhat contradictory. Do you want an 'vla *g;' in C? If so,  
your global will be of type %vla** (you'll load a pointer to the array  
from the global). Its initializer would be a bitcast of a global which  
has some type similar to %vla. If not, and you indeed want a global of  
type %vla*, read on…

> The question is, how can I assign an array of type "{ i32, [5 x  
> float]}" to a global of type "{ i32, [0 x float]}"?

You can't, but declarations and definitions can have differing types.  
For instance:

$ cat a.ll
@g = external global {i32, [0 x float]}

define {i32, [0 x float]}* @f() {
entry:
	ret {i32, [0 x float]}* @g
}
$ cat b.ll
@g = constant {i32, [5 x float]} zeroinitializer

If this is for separate compilation, the linker will automatically  
resolve the type conflict. It does so by replacing all uses of the  
declaration with bitcasts of the definition. Using the same example:

$ llvm-as a.ll; llvm-as b.ll; llvm-link a.bc b.bc | llvm-dis
; ModuleID = '<stdin>'
@g = constant { i32, [5 x float] } zeroinitializer		; <{ i32, [5 x  
float] }*> [#uses=1]

define { i32, [0 x float] }* @f() {
entry:
	ret { i32, [0 x float] }* bitcast ({ i32, [5 x float] }* @g to { i32,  
[0 x float] }*)
}

Internally to your front end, you could do the same thing: Declare the  
global early with its abstract type, and later when the concrete  
storage type is known, use ConstantExpr::getBitCast,  
replaceAllUsesWith, and takeName to do the same thing the linker did  
above.

— Gordon

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/llvm-dev/attachments/20080420/e09e159d/attachment.html>


More information about the llvm-dev mailing list