diff --git a/ExprPrimaryNodes.py b/ExprPrimaryNodes.py
index ab85e8ec09e68f2bc65715fd07c5a0824d77d695..3fa30e00ba8a56132a6a602a21866fc79eaca7ca 100644
--- a/ExprPrimaryNodes.py
+++ b/ExprPrimaryNodes.py
@@ -366,21 +366,30 @@ class AssignNode(ASTNode):
 # cast: castExpr LPAREN castType RPAREN unaryNotPlusMinus
 class CastNode(ASTNode):
     # always list all fields in the init method to show the class structure
-    def __init__(self, parseTree, typeName):
+    def __init__(self, parseTree, typeName, left = None, right = None):
         self.parseTree = parseTree
-        self.left = parseTree.children[1]  # cast: (left)right
-        self.right = makeNodeFromExpr(parseTree.children[3], typeName) # expr
         self.env = None
         self.children = []
         self.typeName = typeName # the type (class/interface) this node belongs under
 
-        if self.left.name == 'expr':
-            self.left = makeNodeFromExpr(self.left, typeName)
-        else: #primitiveType or ArrayType
-            self.left = TypeNode(self.left, typeName)
-        # since a type might be mis-parsed as a name
-        if self.left.__class__.__name__ == 'NameNode':
-            self.left = TypeNode(self.parseTree.children[1], typeName)
+        if left is None or right is None:
+            self.left = parseTree.children[1]  # cast: (left)right
+            self.right = makeNodeFromExpr(parseTree.children[3], typeName) # expr
+
+            if self.left.name == 'expr':
+                self.left = makeNodeFromExpr(self.left, typeName)
+            else: #primitiveType or ArrayType
+                self.left = TypeNode(self.left, typeName)
+            # since a type might be mis-parsed as a name
+            if self.left.__class__.__name__ == 'NameNode':
+                self.left = TypeNode(self.parseTree.children[1], typeName)
+
+        else:
+            # manually induce left and right
+            # for converting string concatenation to a method call
+            # see ExprPrimaryNodes:ExprNode on string concat
+            self.left = left
+            self.right = right
 
         self.children.append(self.left)
         self.children.append(self.right)
@@ -622,23 +631,42 @@ class ExprNode(ASTNode):
                 valueOfNameNode = NameNode(self.parseTree, True, self.typeName, "String.valueOf")
                 valueOfNameNode.env = self.env
 
+                # store these as they could change in step 2
+                leftValueOf = self.left
+                rightValueOf = self.right
+
+                # 2. cast to Object if it is not safe to call String.valueOf
+                safeTypes = ['java.lang.String', 'char', 'int', 'short', 'byte', 'boolean', 'java.lang.Object', 'String']
+
+                if self.left.myType.name not in safeTypes or self.right.myType.name not in safeTypes:
+
+                    # CastNode
+                    # - left = TypeNode
+                    #     - myType = TypeStruct
+                    #         - name = 'java.lang.Object'
+                    #         - typePointer = call link() !
+                    # - right = value of thing being casted
+
+                    # create object TypeNode
+                    objectCastType = TypeNode('VOID', self.typeName)
+                    objectCastType.myType = TypeStruct('java.lang.Object', None)
+                    objectCastType.myType.link(self.env)
+
+                    if self.left.myType.name not in safeTypes:
+                        leftValueOf = CastNode(self.parseTree, self.typeName, objectCastType, self.left)
+
+                    if self.right.myType.name not in safeTypes:
+                        rightValueOf = CastNode(self.parseTree, self.typeName, objectCastType, self.right)
+
+                # 3. call String.valueOf on the variable that needs to be converted
                 if self.left.myType.name != 'java.lang.String':
-                    # 2. Make ArgsNode
-                    leftArg = ArgsNode(self.parseTree, self.typeName, [self.left])
-                    # 3. Put it all together
+                    leftArg = ArgsNode(self.parseTree, self.typeName, [leftValueOf])
                     concatLeft = MethodInvNode(self.parseTree, self.typeName, valueOfNameNode, leftArg)
 
                 if self.right.myType.name != 'java.lang.String':
-                    # 2. Make ArgsNode
-                    rightArg = ArgsNode(self.parseTree, self.typeName, [self.right])
-                    # 3. Put it all together
+                    rightArg = ArgsNode(self.parseTree, self.typeName, [rightValueOf])
                     concatRight = MethodInvNode(self.parseTree, self.typeName, valueOfNameNode, rightArg)
 
-                # 4. Check type to be safe
-                # concatLeft.checkType()
-                # concatRight.checkType()
-
-
             # methodInvoc primary PERIOD ID LPAREN args RPAREN
             # MethodInvNode
             # primary = self.left
@@ -732,8 +760,10 @@ class ExprNode(ASTNode):
             self.code += self.left.code
 
             if self.op == '&&':
+                # if left result == false, break out
                 self.code += p("cmp", "eax", "0")
             elif self.op == '||':
+                # if left result == true, break out
                 self.code += p("cmp", "eax", "1")
 
             self.code += p("je", endLabel, "", " breaking out of " + self.op)
@@ -758,7 +788,7 @@ class ExprNode(ASTNode):
             self.code += p(endLabel + ":", "")
             return
 
-        # String Add TODO
+        # String Add
         if (self.left.myType.name =='java.lang.String' or self.right.myType.name =='java.lang.String') and self.op == '+':
             # ( String.valueOf(right) ).concat( left )
             if not hasattr(self.concatMethodInv, "code"):