Commit Graph

1613 Commits

Author SHA1 Message Date
Doug Gregor
a341300cb0 Switch ClassDecl::getSuperclass() and EnumDecl::getRawType() to interface types.
This has the nice "side effect" of making overrides of generic
functions work better, fixing the remaining type checker issues from
<rdar://problem/15836098>.

Also synthesize the types for derived RawRepresentable conformances
directly rather than going through the type checker, so we get the
interface types right. 



Swift SVN r14066
2014-02-19 00:54:04 +00:00
Chris Lattner
09e49dc2d8 strength reduce SILGen's representation of indexes from being
RValueSource's to RValues.  SILGen doesn't need the generality
of RValueSource.  NFC.


Swift SVN r14015
2014-02-17 23:41:32 +00:00
Chris Lattner
48759e2ae1 strength reduce SILGen's handling of the "value" argument when calling
a setter to use an RValue instead of RValueSource.  NFC.


Swift SVN r14013
2014-02-17 23:35:02 +00:00
Chris Lattner
28903887e7 Rename the internal compiler lexicon from let -> val.
Swift SVN r13992
2014-02-17 16:48:21 +00:00
Doug Gregor
0a52efd530 SIL: Lower DynamicSelf.metatype down to the metatype of the self type.
Swift SVN r13977
2014-02-17 05:35:11 +00:00
Doug Gregor
2134072285 Split open_existential[_ref] out as their own instructions.
Riding off of project_existential[_ref] was convenient, but the
resuls are used quite differently. Note that open_existential[_ref]
still don't print/parse reasonably yet.



Swift SVN r13878
2014-02-13 23:42:23 +00:00
Chris Lattner
12196c17ba Now that we always have funcdecls for getters and setters, we don't need
SILDeclRef::Getter/Setter and the complexity therein.  Switch the world
to make SILDeclRef::Func's instead of them.  NFC.


Swift SVN r13875
2014-02-13 23:11:29 +00:00
Joe Groff
8a92d5e246 SILGen: Handle capture of 'self' in a derived class 'init' method.
'self' is formally a 'val', but we allocate a mutable box for it to accommodate self-rebinding by super.init, and we tried to pass the box owner and address as the closure parameters instead of the expected pass-by-value semantics. Fix it to properly handle the capture by value.

Swift SVN r13824
2014-02-12 07:06:38 +00:00
Doug Gregor
8f0a7c5e19 Only use Objective-C dispatch to a constructor if it is actuallly @objc.
<rdar://problem/15967182> fixed the inference of @objc for
initializers, but our SILGen predicate deciding whether to perform
Objective-C dispatch was failing to heed the @objc bit on
constructors. Fixes <rdar://problem/16041090>.


Swift SVN r13787
2014-02-11 22:41:02 +00:00
Doug Gregor
6d1f80f331 Bubble the covariant conversions to the outermost relevant call.
When applying a function that was produced via a covariant function
conversion, strip off that covariant function conversion and introduce
a covariant (function or return) conversion outside of the
application. This allows us to perform the covariant conversion very
late, eliminating the need to produce reabstraction thunks for any
call to a DynamicSelf method.


Swift SVN r13779
2014-02-11 06:29:33 +00:00
Chris Lattner
bc005219d1 Implement most of support for properties in function scope, part of rdar://15922884.
Most of the complexity here is teaching SILGen how to handle closed-over direct 
accesses to observing properties, since all of the getter/setter/willSet/didSet
members of the property are actually full closures when in a function body.

We generate correct but really terrible code here, since the setter captures the
willset/didset members themselves.  I'm not worrying about the performance of 
this construct though, functionality is what matters.


Swift SVN r13778
2014-02-11 06:23:14 +00:00
Doug Gregor
12c064d501 IR generation for DynamicSelf method invocations on existentials.
When projecting an existential into an opened archetype, bind the
archetype with metadata and witness tables extracted from the
existential. Tweak SILGen so that it doesn't destroy the opened
archetype value an extra two times.

Use an executable testcase to ensure end-to-end operation, because we
still don't have a parsable form existential projection to opened
archetype instructions.



Swift SVN r13755
2014-02-10 18:47:24 +00:00
Doug Gregor
474016398f Model references to DynamicSelf methods on existentials by opening the existential.
Introduce a new expression kind, OpenExistentialExpr, that "opens" up
an existential value into a value of a fresh archetype type that
represents the dynamic type of the existential. That value can be
referenced (via an OpaqueValueExpr) within the within the
subexpression of OpenExistentialExpr. For example, a call to a
DynamicSelf method on an existential looks something like this:

        (open_existential_expr implicit type='P'
          (opaque_value_expr implicit type='opened P' @ 0x7fd95207c290
          unique)
          (load_expr implicit type='P'
            (declref_expr type='@lvalue P' decl=t.(file).func
          decl.p@t.swift:5:37 specialized=no))
          (erasure_expr implicit type='P'
            (call_expr type='opened P'
              (archetype_member_ref_expr type='() -> opened P'
          decl=t.(file).P.f@t.swift:2:8 [with Self=opened P]
                (opaque_value_expr implicit type='opened P' @
          0x7fd95207c290 unique))
              (tuple_expr type='()')))))

Note that we're using archetype_member_ref_expr rather than
existential_member_ref_expr, because the call is operating on the
opaque_value_expr of archetype type. The outer erasure turns the
archetype value back into an existential value.

The SILGen side of this is somewhat incomplete; we're using
project_existential[_ref] to open the existential, which is almost
correct: it gives us access to the value as an archetype, but IRGen
doesn't know to treat the archetype type as a fresh archetype whose
conformances come from the existential. Additionally, the output of
the opened type is not properly parsable. I'll fix this in follow-on
commits.

Finally, the type checker very narrowly introduces support for
OpenExistentialExpr as it pertains to DynamicSelf. However, this can
generalize to support all accesses into existentials, eliminating the
need for ExistentialMemberRef and ExistentialSubscript in the AST and
protocol_method in SIL, as well as enabling more advanced existential
features should we want them later.



Swift SVN r13740
2014-02-10 06:44:44 +00:00
Chris Lattner
f9a83fdc33 Implement the first half of <rdar://problem/15922884> support non-member didset/willset properties
Observing properties now work fine as globals.  Local variables still need some work though.



Swift SVN r13736
2014-02-10 05:43:04 +00:00
Chris Lattner
d690a63a87 progress towards non-member observing properties:
- Add a "isDirectPropertyAccess" bit to DeclRefExpr, serving the 
   same purpose as MemberRefExprs for non-member properties.
 - Teach sema to synthesize correct non-member get/set implementations
   for observing properties.
 - Teach silgen to handle the isDirectPropertyAccess bit.



Swift SVN r13600
2014-02-06 22:34:37 +00:00
Joe Groff
e86e17c8a6 SILGen: Use interface types in RValueEmitter's implementation.
Cut over to using interface types and injecting context from the SILFunction as needed in all of the expression lowering code.

Reapplying this now that r13036 has been reapplied as r13485.

Swift SVN r13489
2014-02-05 18:35:16 +00:00
Chris Lattner
7532213f4a simplify the SIL string_literal instruction to only produce a single value,
which is the address of the string data.  Have SILGen compute and produce the
isASCII bit as an integer literal, and remove the logic from IRGen.

This overall approach is simpler and enables better SIL-level optimizations.


Swift SVN r13363
2014-02-03 19:10:37 +00:00
Chris Lattner
96947b2606 Change silgen to lower string literal lengths to an explicit value, instead of using
the result of the string_literal instruction.

This fixes:
<rdar://problem/15883849> Diagnostic CCP should be able to fold operations on string_literal lengths

I will follow up with cleanups this enables.




Swift SVN r13361
2014-02-03 18:26:46 +00:00
Doug Gregor
9f72215bba Basic SIL- and IR-generation support for trivial uses of DynamicSelf.
Introduce a new AST node to capture the covariant function type
conversion for DynamicSelf. This conversion differs from the normal
function-conversion expressions because it isn't inherently type-safe;
type safety is assured through DynamicSelf.  

On the SIL side, map DynamicSelf down to the type of the declaring
class to keep the SIL type system consistent. Map the new
CovariantFunctionConversionExpr down to a convert_function
instruction, slightly loosening the constraints on convert_function to
allow for this (it's always been ABI-compatible-only conversions
anyway).

We currently generate awful SIL when calling a DynamicSelf method,
because SILGenApply doesn't know how to deal with the implicit return
type adjustment associated with the covariant function
conversion. That optimization will follow; at least what we have here
is (barely) functional.


Swift SVN r13286
2014-02-01 04:09:00 +00:00
Michael Gottesman
74165eef2b Revert "Basic SIL- and IR-generation support for trivial uses of DynamicSelf."
This reverts commit r13269. It broke the build.

Swift SVN r13281
2014-02-01 02:31:39 +00:00
Doug Gregor
c25b14b1bd Basic SIL- and IR-generation support for trivial uses of DynamicSelf.
Introduce a new AST node to capture the covariant function type
conversion for DynamicSelf. This conversion differs from the normal
function-conversion expressions because it isn't inherently type-safe;
type safety is assured through DynamicSelf.

On the SIL side, map DynamicSelf down to the type of the declaring
class to keep the SIL type system consistent. Map the new
CovariantFunctionConversionExpr down to a convert_function
instruction, slightly loosening the constraints on convert_function to
allow for this (it's always been ABI-compatible-only conversions
anyway).

We currently generate awful SIL when calling a DynamicSelf method,
because SILGenApply doesn't know how to deal with the implicit return
type adjustment associated with the covariant function
conversion. That optimization will follow; at least what we have here
is (barely) functional.

Swift SVN r13269
2014-02-01 01:20:26 +00:00
Chris Lattner
3e08673772 Introduce patterns for self arguments to ctors and dtors, making them uniform
with FuncDecls.  This allows us to eliminate special case code for handling
self in various parts of the compiler.

This also improves loc info (debug info and AST info) because 'self' now
has a location instead of being invalid.

I also took the opportunity to factor a bunch of places creating self decls
to use similar patterns and less copy and paste code.



Swift SVN r13196
2014-01-31 02:17:22 +00:00
Doug Gregor
f1be1ed572 Implement super mesage sends for @objc property and subscript getters/setters.
Fixes <rdar://problem/15933008>.


Swift SVN r13100
2014-01-29 07:45:53 +00:00
Joe Groff
9f698b67d8 Revert "SILGen: Use interface types in RValueEmitter's implementation."
This reverts commit r13053. It's dependent on 13036, which was reverted.

Swift SVN r13065
2014-01-28 22:05:34 +00:00
Joe Groff
357a242034 SILGen: Use interface types in RValueEmitter's implementation.
Cut over to using interface types and injecting context from the SILFunction as needed in all of the expression lowering code.

Swift SVN r13053
2014-01-28 05:25:57 +00:00
Chris Lattner
8735a76b0b Simplify emitRValueForPropertyLoad and make it work when we can have
rvalues that are both computed and have storage.


Swift SVN r13010
2014-01-27 22:10:34 +00:00
Chris Lattner
a945271aa8 Now that properties in protocols are always computed, and that StoredObjC
properties have accessors, we have an amazing property: everything that we
want to form a getter or setter for ... really has one! I suspect many things
can be simplified now, but the first on the chopping block is 
StorageDecl::getGetterType (and its three friends) which is now always exactly
just getGetter()->getType().



Swift SVN r12983
2014-01-27 06:17:28 +00:00
Chris Lattner
ddc5ca81d6 Fix <rdar://problem/15858869> *all* objc accessors disabled in init methods, not just for self
This patch: 
 - Changes sema to set the "IsDirectPropertyAccess" on MemberRefExprs
   in inits/destructors that should be done directly because they are
   on the local object.
 - Removes the "SGF.AlwaysDirectStoredPropertyAccess" bool in SILGen,
   which was the source of the problem above and was otherwise problematic.

This will get a bit simpler when -enable-new-objc-properties rolls out. 


Swift SVN r12967
2014-01-26 07:23:42 +00:00
Chris Lattner
91fb51100d Introduce a new kind of StorageDecl called StoredObjC. These are
properties that are (usually) accessed through getters and setters, but
which have storage.  Nothing generates these yet.


Swift SVN r12902
2014-01-24 05:15:11 +00:00
Chris Lattner
690e8a38af switch places the ignore the result of an rvalue to allow it to be +0. No
impact on stdlib or testsuite.


Swift SVN r12879
2014-01-23 22:06:21 +00:00
Chris Lattner
246c301bf5 enhance emission of tupleelementexprs to know about +0 values to
avoid temporaries.  This exposed a bug in the RValue tuple scalarization
logic handling +0 values.  This has no impact on the stdlib.


Swift SVN r12874
2014-01-23 20:17:32 +00:00
Chris Lattner
c6a334ab6e teach SILGenFunction::emitLoad that clients allowing +0 results don't
need the load (and temporary, and cleanup) to actually be emitted for
address-only operands.  They can just use the physical lvalue as the +0 base.

In this example:
struct GenericStruct<T> {
  var a : T
  var b : Int

  func getA() -> T {
    return a
  }

  func getB() -> Int {
    return b
  }
}

we used to produce:

sil @_TFV2t213GenericStruct4getAU__fGS0_Q__FT_Q_ : $@cc(method) @thin <$T_0_0> (@out $T_0_0, @in GenericStruct<$T_0_0>) -> () {
bb0(%0 : $*T, %1 : $*GenericStruct<T>):
  debug_value_addr %1 : $*GenericStruct<T>  // let self // id: %2
  %3 = alloc_stack $GenericStruct<T>              // users: %8, %7, %5, %4
  copy_addr %1 to [initialization] %3#1 : $*GenericStruct<T> // id: %4
  %5 = struct_element_addr %3#1 : $*GenericStruct<T>, #a // user: %6
  copy_addr %5 to [initialization] %0 : $*T       // id: %6
  destroy_addr %3#1 : $*GenericStruct<T>          // id: %7
  dealloc_stack %3#0 : $*@local_storage GenericStruct<T> // id: %8
  destroy_addr %1 : $*GenericStruct<T>            // id: %9
  %10 = tuple ()                                  // user: %11
  return %10 : $()                                // id: %11
}

sil @_TFV2t213GenericStruct4getBU__fGS0_Q__FT_Si : $@cc(method) @thin <$T_0_0> (@in GenericStruct<$T_0_0>) -> Int64 {
bb0(%0 : $*GenericStruct<T>):
  debug_value_addr %0 : $*GenericStruct<T>  // let self // id: %1
  %2 = alloc_stack $GenericStruct<T>              // users: %7, %6, %4, %3
  copy_addr %0 to [initialization] %2#1 : $*GenericStruct<T> // id: %3
  %4 = struct_element_addr %2#1 : $*GenericStruct<T>, #b // user: %5
  %5 = load %4 : $*Int64                          // user: %9
  destroy_addr %2#1 : $*GenericStruct<T>          // id: %6
  dealloc_stack %2#0 : $*@local_storage GenericStruct<T> // id: %7
  destroy_addr %0 : $*GenericStruct<T>            // id: %8
  return %5 : $Int64                              // id: %9
}

now we produce:

sil @_TFV2t213GenericStruct4getAU__fGS0_Q__FT_Q_ : $@cc(method) @thin <$T_0_0> (@out $T_0_0, @in GenericStruct<$T_0_0>) -> () {
bb0(%0 : $*T, %1 : $*GenericStruct<T>):
  debug_value_addr %1 : $*GenericStruct<T>  // let self // id: %2
  %3 = struct_element_addr %1 : $*GenericStruct<T>, #a // user: %4
  copy_addr %3 to [initialization] %0 : $*T       // id: %4
  destroy_addr %1 : $*GenericStruct<T>            // id: %5
  %6 = tuple ()                                   // user: %7
  return %6 : $()                                 // id: %7
}

sil @_TFV2t213GenericStruct4getBU__fGS0_Q__FT_Si : $@cc(method) @thin <$T_0_0> (@in GenericStruct<$T_0_0>) -> Int64 {
bb0(%0 : $*GenericStruct<T>):
  debug_value_addr %0 : $*GenericStruct<T>  // let self // id: %1
  %2 = struct_element_addr %0 : $*GenericStruct<T>, #b // user: %3
  %3 = load %2 : $*Int64                          // user: %5
  destroy_addr %0 : $*GenericStruct<T>            // id: %4
  return %3 : $Int64                              // id: %5
}

This cuts about 120 lines out of the stdlib (so, about 40 temporaries).


Swift SVN r12871
2014-01-23 19:44:43 +00:00
Dave Zarzycki
6eba6ceeeb Zap accumlated unused variable warnings in non-assert builds
Swift SVN r12861
2014-01-23 08:11:37 +00:00
Chris Lattner
87fbce6a1a Progress on <rdar://problem/15867140> [string perf] member_ref_expr on an rvalue producing unnecessary retains/releases
- Remove my previous local hack.
- Add a new flag to SGFContext indicating that clients are ok with +0 rvalues.
- Teach emitRValueForPropertyLoad and emitRValueForDecl how to work with +0 rvalues.

This allows us to avoid retaining bases in arbitrarily nested struct rvalue
member_ref_expr's.  For example, this:

class SomeClass {}

struct AnotherStruct {
  var x : Int
  var c : SomeClass
}

struct StructMemberTest {
  var c1 : SomeClass, c2 : SomeClass
  var s : AnotherStruct

  func testRecursiveStruct() -> Int {
    return s.x
  }
}

used to compile to:

sil @_TFV1t16StructMemberTest19testRecursiveStructfS0_FT_Si : $@cc(method) @thin (@owned StructMemberTest) -> Int64 {
bb0(%0 : $StructMemberTest):
  debug_value %0 : $StructMemberTest  // let self // id: %1
  %2 = struct_extract %0 : $StructMemberTest, #s  // user: %3
  %3 = copy_value %2 : $AnotherStruct             // users: %5, %4
  %4 = struct_extract %3 : $AnotherStruct, #x     // user: %7
  destroy_value %3 : $AnotherStruct               // id: %5
  destroy_value %0 : $StructMemberTest            // id: %6
  return %4 : $Int64                              // id: %7
}

and now it compiles to:

sil @_TFV1t16StructMemberTest19testRecursiveStructfS0_FT_Si : $@cc(method) @thin (@owned StructMemberTest) -> Int64 {
bb0(%0 : $StructMemberTest):
  debug_value %0 : $StructMemberTest  // let self // id: %1
  %2 = struct_extract %0 : $StructMemberTest, #s  // user: %3
  %3 = struct_extract %2 : $AnotherStruct, #x     // user: %5
  destroy_value %0 : $StructMemberTest            // id: %4
  return %3 : $Int64                              // id: %5
}

There is more that can come from this, but it is a start.  This cuts out 50 retain/release pairs from the stdlib.



Swift SVN r12857
2014-01-23 06:54:02 +00:00
Dave Abrahams
d58caea0cd Revert "Zap accumlated warnings in non-assert builds"
This reverts r12850, which broke the build for me.

Swift SVN r12856
2014-01-23 06:47:29 +00:00
Dave Zarzycki
17eb84d9c6 Zap accumlated warnings in non-assert builds
Swift SVN r12850
2014-01-23 05:45:24 +00:00
Chris Lattner
fc16e213fe Remove DestroyAddr/CleanupRValue/CleanupMaterializedValue.
All of the clients can use enterDestroyCleanup.


Swift SVN r12830
2014-01-23 00:49:36 +00:00
Chris Lattner
2cf6d814c7 more tidying:
- Strength reduce the interface to LogicalPathComponent::getMaterialized
   to now just return a SILValue for the address.  The full "Materialize"
   structure hasn't been needed since MaterializeExpr got removed.
 - Move 'struct Materialize' out of SILGen.h into SILGenLValues.cpp now
   that it is only used for logical property materialization.
 - Drop the dead 'loc' argument on DeallocStackCleanup.  The location is
   already specified when the cleanup is emitted.


Swift SVN r12827
2014-01-23 00:43:20 +00:00
Chris Lattner
5a557539cd fix a missing SGFContext passdown which would cause an extra copy for
address-only collections (if we ever had such a thing).


Swift SVN r12824
2014-01-23 00:23:29 +00:00
Chris Lattner
6e609bc886 tidy up various code formatting things and adopt
emitRValueAsSingleValue in more places to simplify code. NFC.



Swift SVN r12822
2014-01-23 00:15:49 +00:00
Doug Gregor
f4e6c85f62 Make sure to specialize a non-capturing closure in a generic context.
Fixes the rest of <rdar://problem/15883734>.


Swift SVN r12812
2014-01-22 23:15:05 +00:00
Chris Lattner
84f9919016 introduce a SGF::emitRValueAsSingleValue helper function to wrap a common
and repetitive pattern.


Swift SVN r12808
2014-01-22 22:51:55 +00:00
Chris Lattner
b782bd4c56 'ignored' SGFContext's are also dead, remove them too.
Swift SVN r12799
2014-01-22 22:27:48 +00:00
Chris Lattner
7ee9d7070e The 'ChildOfLoad' and 'Ungeneralized' forms of SGFContext are not used,
remove them.


Swift SVN r12797
2014-01-22 22:21:23 +00:00
Chris Lattner
7cd0f1739a A big part of handling address-only types is making sure that various
emission routines use the SGFContext passed in.  To help with this and
to help the handshake, add a new "isInContext()" representation to 
ManagedValue.  This makes the code producing and consuming these more
explicit.  NFC.


Swift SVN r12783
2014-01-22 21:31:44 +00:00
Sean Callanan
3bc24605fd Updated the signature for emitReferenceToDecl to
take only the arguments LLDB uses, and also to
have a more accurate name.

<rdar://problem/15878172>


Swift SVN r12760
2014-01-22 19:03:52 +00:00
Chris Lattner
8fed381d46 the 'self' argument of SuperRefExpr and RebindSelfInConstructorExpr are always VarDecls,
use it instead of ValueDecl since it is more specific.


Swift SVN r12754
2014-01-22 18:25:19 +00:00
Chris Lattner
b457be6a9f SGF::emitLValueForDecl only works on VarDecls, make its prototype more specific
to reflect that.


Swift SVN r12753
2014-01-22 18:20:06 +00:00
Chris Lattner
b13719be22 reapply r12727 (passing an SGFContext down to emitGetAccessor from
emitRValueForDecl when we have it), now with a testcase.  We formerly 
compiled this:

protocol P {}
var lp : P { get: }

func f() -> P {
  return lp
}

into:

sil @_TF3let1fFT_PS_1P_ : $@thin (@out P) -> () {
bb0(%0 : $*P):
  // function_ref let.lp.getter : let.P
  %1 = function_ref @_TF3letg2lpPS_1P_ : $@thin (@out P) -> () // user: %3
  %2 = alloc_stack $P                             // users: %5, %4, %3
  %3 = apply %1(%2#1) : $@thin (@out P) -> ()
  copy_addr [take] %2#1 to [initialization] %0 : $*P // id: %4
  dealloc_stack %2#0 : $*@local_storage P         // id: %5
  %6 = tuple ()                                   // user: %7
  return %6 : $()                                 // id: %7
}


we now avoid the copy:

sil @_TF3let1fFT_PS_1P_ : $@thin (@out P) -> () {
bb0(%0 : $*P):
  // function_ref let.lp.getter : let.P
  %1 = function_ref @_TF3letg2lpPS_1P_ : $@thin (@out P) -> () // user: %2
  %2 = apply %1(%0) : $@thin (@out P) -> ()
  %3 = tuple ()                                   // user: %4
  return %3 : $()                                 // id: %4
}



Swift SVN r12748
2014-01-22 17:51:38 +00:00
Chris Lattner
ba6bc88399 revert r12727, I didn't include a testcase.
Swift SVN r12746
2014-01-22 17:46:37 +00:00