001 /* Copyright (c) 2005-2008, Torbjorn Ekman 002 * 2011, Jesper Öqvist <jesper.oqvist@cs.lth.se> 003 * All rights reserved. 004 * 005 * Redistribution and use in source and binary forms, with or without 006 * modification, are permitted provided that the following conditions are met: 007 * 008 * 1. Redistributions of source code must retain the above copyright notice, 009 * this list of conditions and the following disclaimer. 010 * 011 * 2. Redistributions in binary form must reproduce the above copyright notice, 012 * this list of conditions and the following disclaimer in the documentation 013 * and/or other materials provided with the distribution. 014 * 015 * 3. Neither the name of the copyright holder nor the names of its 016 * contributors may be used to endorse or promote products derived from this 017 * software without specific prior written permission. 018 * 019 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 020 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 021 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 022 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE 023 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 024 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 025 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 026 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 027 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 028 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 029 * POSSIBILITY OF SUCH DAMAGE. 030 */ 031 032 aspect Variables { 033 VariableDeclaration implements Variable; 034 syn boolean VariableDeclaration.isParameter() = false; 035 // 4.5.3 036 syn boolean VariableDeclaration.isClassVariable() = false; 037 syn boolean VariableDeclaration.isInstanceVariable() = false; 038 syn boolean VariableDeclaration.isMethodParameter() = false; 039 syn boolean VariableDeclaration.isConstructorParameter() = false; 040 syn boolean VariableDeclaration.isExceptionHandlerParameter() = false; 041 syn boolean VariableDeclaration.isLocalVariable() = true; 042 // 4.5.4 043 syn boolean VariableDeclaration.isFinal() = getModifiers().isFinal(); 044 syn boolean VariableDeclaration.isVolatile() = getModifiers().isVolatile(); 045 syn boolean VariableDeclaration.isBlank() = !hasInit(); 046 syn boolean VariableDeclaration.isStatic() = false; 047 048 syn String VariableDeclaration.name() = getID(); 049 050 syn lazy Constant VariableDeclaration.constant() = type().cast(getInit().constant()); 051 052 FieldDeclaration implements Variable; 053 syn boolean FieldDeclaration.isParameter() = false; 054 // 4.5.3 055 syn boolean FieldDeclaration.isClassVariable() = isStatic() || hostType().isInterfaceDecl(); 056 syn boolean FieldDeclaration.isInstanceVariable() = (hostType().isClassDecl() || hostType().isAnonymous() )&& !isStatic(); 057 syn boolean FieldDeclaration.isMethodParameter() = false; 058 syn boolean FieldDeclaration.isConstructorParameter() = false; 059 syn boolean FieldDeclaration.isExceptionHandlerParameter() = false; 060 syn boolean FieldDeclaration.isLocalVariable() = false; 061 062 syn boolean FieldDeclaration.isBlank() = !hasInit(); 063 064 syn String FieldDeclaration.name() = getID(); 065 syn lazy Constant FieldDeclaration.constant() = type().cast(getInit().constant()); 066 067 ParameterDeclaration implements Variable; 068 syn boolean ParameterDeclaration.isParameter() = true; 069 070 // 4.5.3 071 syn boolean ParameterDeclaration.isClassVariable() = false; 072 syn boolean ParameterDeclaration.isInstanceVariable() = false; 073 inh boolean ParameterDeclaration.isMethodParameter(); 074 inh boolean ParameterDeclaration.isConstructorParameter(); 075 inh boolean ParameterDeclaration.isExceptionHandlerParameter(); 076 syn boolean ParameterDeclaration.isLocalVariable() = false; 077 078 // 4.5.3 079 eq ConstructorDecl.getParameter().isMethodParameter() = false; 080 eq ConstructorDecl.getParameter().isConstructorParameter() = true; 081 eq ConstructorDecl.getParameter().isExceptionHandlerParameter() = false; 082 eq MethodDecl.getParameter().isMethodParameter() = true; 083 eq MethodDecl.getParameter().isConstructorParameter() = false; 084 eq MethodDecl.getParameter().isExceptionHandlerParameter() = false; 085 eq BasicCatch.getParameter().isMethodParameter() = false; 086 eq BasicCatch.getParameter().isConstructorParameter() = false; 087 eq BasicCatch.getParameter().isExceptionHandlerParameter() = true; 088 089 eq Program.getChild().isMethodParameter() = false; 090 eq Program.getChild().isConstructorParameter() = false; 091 eq Program.getChild().isExceptionHandlerParameter() = false; 092 093 // 4.5.4 094 syn boolean ParameterDeclaration.isFinal() = getModifiers().isFinal(); 095 syn boolean ParameterDeclaration.isVolatile() = getModifiers().isVolatile(); 096 syn boolean ParameterDeclaration.isBlank() = true; 097 syn boolean ParameterDeclaration.isStatic() = false; 098 099 syn String ParameterDeclaration.name() = getID(); 100 101 syn boolean ParameterDeclaration.hasInit() = false; 102 syn Expr ParameterDeclaration.getInit() { throw new UnsupportedOperationException(); } 103 syn Constant ParameterDeclaration.constant() { throw new UnsupportedOperationException(); } 104 105 syn String VariableDecl.name() = getID(); 106 107 } 108 109 aspect VariableDeclarationTransformation { 110 // when splitting a FieldDecl into multiple FieldDeclarations, provide every FieldDeclaration with a reference 111 // to the original FieldDecl; if only a single FieldDeclaration results, no reference is stored 112 private FieldDecl FieldDeclaration.fieldDecl = null; 113 public FieldDecl FieldDeclaration.getFieldDecl() { 114 return fieldDecl; 115 } 116 public void FieldDeclaration.setFieldDecl(FieldDecl fieldDecl) { 117 this.fieldDecl = fieldDecl; 118 } 119 120 // FieldDecl with single VariableDecl -> FieldDeclaration 121 rewrite FieldDecl { 122 when(getNumVariableDecl() == 1) 123 to FieldDeclaration { 124 FieldDeclaration decl = getVariableDecl(0).createFieldDeclarationFrom(getModifiers(), getTypeAccess()); 125 decl.setStart(start); // copy location information 126 decl.setEnd(end); // copy location information 127 return decl; 128 } 129 } 130 131 // FieldDecl with multiple VariableDecl to FieldDeclaration list. 132 rewrite FieldDecl in TypeDecl.getBodyDecl() { 133 when(getNumVariableDecl() > 1) 134 to List { 135 List varList = new List(); 136 for (int j = 0; j < getNumVariableDecl(); j++) { 137 FieldDeclaration f = getVariableDecl(j).createFieldDeclarationFrom( 138 (Modifiers) getModifiers().treeCopyNoTransform(), 139 (Access) getTypeAccess().treeCopyNoTransform() 140 ); 141 if (j == 0) { 142 f.setStart(start); 143 } else { 144 f.getModifiersNoTransform().clearLocations(); 145 f.getTypeAccessNoTransform().clearLocations(); 146 } 147 f.setFieldDecl(this); 148 varList.add(f); 149 } 150 return varList; 151 } 152 } 153 154 public void ASTNode.clearLocations() { 155 setStart(0); 156 setEnd(0); 157 for (int i = 0; i < getNumChildNoTransform(); i++) { 158 getChildNoTransform(i).clearLocations(); 159 } 160 } 161 162 163 syn lazy List<VariableDeclaration> VarDeclStmt.getSingleDeclList() { 164 List<VariableDeclaration> decls = new List<VariableDeclaration>(); 165 for (int i = 0; i < getNumVariableDecl(); ++i) { 166 VariableDecl varDecl = getVariableDecl(i); 167 VariableDeclaration decl = varDecl.createVariableDeclarationFrom(getModifiers(), getTypeAccess()); 168 decls.add(decl); 169 } 170 return decls; 171 } 172 173 public VariableDeclaration VariableDecl.createVariableDeclarationFrom(Modifiers modifiers, Access type) { 174 // TODO should treeCopy modifiers init opt etc??? 175 VariableDeclaration decl = new VariableDeclaration( 176 modifiers, 177 type.addArrayDims(getDimsList()), 178 getID(), 179 getInitOpt() 180 ); 181 decl.setStart(start); // copy location information 182 decl.setEnd(end); // copy location information 183 decl.IDstart = IDstart; 184 decl.IDend = IDend; 185 return decl; 186 } 187 188 public FieldDeclaration VariableDecl.createFieldDeclarationFrom(Modifiers modifiers, Access type) { 189 // TODO should treeCopy modifiers init opt etc??? 190 FieldDeclaration decl = new FieldDeclaration( 191 modifiers, 192 type.addArrayDims(getDimsList()), 193 getID(), 194 getInitOpt() 195 ); 196 decl.setStart(start); // copy location information 197 decl.setEnd(end); // copy location information 198 decl.IDstart = IDstart; 199 decl.IDend = IDend; 200 return decl; 201 } 202 }