예제 #1
0
  /** Immediately refreshes all globals using the backing database. */
  public synchronized void refreshGlobals() {
    bootstrapOnce.ensure();

    Database database = getDatabase();
    LOGGER.info("Loading globals from [{}]", database.getName());

    Query<Object> globalsQuery =
        Query.from(Object.class).where("_id = ?", GLOBALS_ID).using(database).noCache();

    State newGlobals = State.getInstance(globalsQuery.first());

    if (newGlobals == null) {
      newGlobals = State.getInstance(globalsQuery.master().first());
    }

    if (newGlobals == null) {
      newGlobals = new State();
      newGlobals.setDatabase(database);
      newGlobals.setId(GLOBALS_ID);
      newGlobals.save();
    }

    globals = newGlobals;
    lastGlobalsUpdate = new Date();
    fieldsCache.reset();
    metricFieldsCache.reset();
    indexesCache.reset();
  }
예제 #2
0
파일: Main.java 프로젝트: damorim/pbicc
 public static void getExtraPutExtraPairs() {
   Map<String, CompilationUnit> asts = State.getInstance().astMap();
   for (Map.Entry<String, CompilationUnit> entry : asts.entrySet()) {
     KeysVisitor kv = new KeysVisitor();
     kv.visit(entry.getValue(), null);
     State.getInstance().pgMap().put(entry.getKey(), kv.getPGs());
   }
 }
예제 #3
0
  @Override
  public int compare(Object x, Object y) {
    State xState = State.getInstance(x);
    State yState = State.getInstance(y);

    Object xValue = xState != null ? filter(xState.getByPath(field)) : null;
    Object yValue = yState != null ? filter(yState.getByPath(field)) : null;

    return ObjectUtils.compare(xValue, yValue, isNullGreatest);
  }
예제 #4
0
  /** Creates an object represented by the given {@code typeId} and {@code id}. */
  public Object createObject(UUID typeId, UUID id) {
    bootstrapOnce.ensure();

    Class<?> objectClass = null;
    ObjectType type = null;
    if (typeId != null && !GLOBALS_ID.equals(id)) {

      if (typeId.equals(id)) {
        objectClass = ObjectType.class;

      } else {
        type = getTypeById(typeId);
        if (type != null) {
          objectClass = type.isAbstract() ? Record.class : type.getObjectClass();
        }
      }
    }

    boolean hasClass = true;
    if (objectClass == null) {
      objectClass = Record.class;
      hasClass = false;
    }

    Object object = SubstitutionUtils.newInstance(objectClass);
    State state;

    try {
      state = State.getInstance(object);

    } catch (IllegalArgumentException error) {
      object = TypeDefinition.getInstance(Record.class).newInstance();
      state = State.getInstance(object);
      hasClass = false;
    }

    state.setDatabase(getDatabase());
    state.setId(id);
    state.setTypeId(typeId);

    if (type != null) {
      if (!hasClass) {
        for (ObjectField field : type.getFields()) {
          Object defaultValue = field.getDefaultValue();
          if (defaultValue != null) {
            state.put(field.getInternalName(), defaultValue);
          }
        }
      }
    }

    return object;
  }
예제 #5
0
파일: Main.java 프로젝트: damorim/pbicc
  public static void getICCLinkResults() {
    Map<String, CompilationUnit> asts = State.getInstance().astMap();
    ICCLinkFindingResults results = new ICCLinkFindingResults();
    State.getInstance().setICCResults(results);

    for (Map.Entry<String, CompilationUnit> entry : asts.entrySet()) {
      CFPVisitor cfpVisitor = new CFPVisitor(results);
      cfpVisitor.visit(entry.getValue(), null);
    }

    results.propagate();

    for (Map.Entry<String, CompilationUnit> entry : asts.entrySet()) {
      ICCLinkFinder.findICCLinks(entry.getValue(), results);
    }
  }
예제 #6
0
 @Override
 public Object clone() {
   Object clone = TypeDefinition.getInstance(getClass()).newInstance();
   State cloneState = State.getInstance(clone);
   cloneState.setDatabase(state.getDatabase());
   cloneState.setStatus(state.getStatus());
   cloneState.setValues(state.getSimpleValues());
   return clone;
 }
예제 #7
0
파일: Main.java 프로젝트: damorim/pbicc
  // create dependency graph
  public static DirectedGraph<String, DefaultEdge> createDependencyGraph() {
    DirectedGraph<String, DefaultEdge> g =
        new DefaultDirectedGraph<String, DefaultEdge>(DefaultEdge.class);

    // add vertices
    for (String key : State.getInstance().pgMap().keySet()) {
      g.addVertex(key);
    }

    // add edges
    for (Map.Entry<String, PutsAndGets> entry1 : State.getInstance().pgMap().entrySet()) {
      PutsAndGets pg1 = entry1.getValue();

      for (Map.Entry<String, PutsAndGets> entry2 : State.getInstance().pgMap().entrySet()) {
        PutsAndGets pg2 = entry2.getValue();

        if (pg2.isDep(pg1)) {
          g.addEdge(entry2.getKey(), entry1.getKey());
        }
      }
    }

    return g;
  }
예제 #8
0
  @Override
  public boolean equals(Object object) {
    if (this == object) {
      return true;

    } else if (object != null) {
      try {
        return getState().equals(State.getInstance(object));

      } catch (IllegalArgumentException error) {
        return false;
      }

    } else {
      return false;
    }
  }
예제 #9
0
파일: Tile.java 프로젝트: softarn/Civ6
 public void deselect() {
   State st = State.getInstance();
   if (st.getSelectedTile().equals(this)) {
     st.setSelectedTile(null);
     st.setTileState(TileUnSelected);
     selected = false;
     if (hasCity()) {
       st.setSelectedCity(null);
       st.setCityState(CityUnSelected);
     }
     if (hasUnit()) {
       st.setSelectedUnit(null);
       st.setUnitState(UnitUnSelected);
     }
     view.repaint();
   }
 }
예제 #10
0
파일: Tile.java 프로젝트: softarn/Civ6
 public void select() {
   State st = State.getInstance();
   if (st.getTileState() == TileSelected) {
     State.getSelectedTile().deselect();
   }
   st.setSelectedTile(this);
   st.setTileState(TileSelected);
   if (hasCity()) {
     st.setSelectedCity(city);
     st.setCityState(CitySelected);
   }
   if (hasUnit()) {
     st.setSelectedUnit(unit);
     st.setUnitState(UnitSelected);
   }
   selected = true;
   view.repaint();
 }
예제 #11
0
    @Override
    public final boolean evaluate(PredicateParser parser, Object object, Predicate predicate) {
      State state = State.getInstance(object);
      ComparisonPredicate comparison = (ComparisonPredicate) predicate;
      Object keyValue = state.getByPath(comparison.getKey());
      List<Object> values = comparison.resolveValues(state.getDatabase());

      if (keyValue == null) {
        keyValue = Query.MISSING_VALUE;
        return compare(state, keyValue, values);

      } else if (keyValue instanceof Iterable) {
        for (Object item : (Iterable<?>) keyValue) {
          if (evaluateOne(state, item, values)) {
            return true;
          }
        }
        return false;

      } else {
        return evaluateOne(state, keyValue, values);
      }
    }
예제 #12
0
  /** Immediately refreshes all types using the backing database. */
  public synchronized void refreshTypes() {
    bootstrapOnce.ensure();

    Database database = getDatabase();
    try {

      TypesCache temporaryTypes = temporaryTypesLocal.get();
      if (temporaryTypes == null) {
        temporaryTypes = new TypesCache();
        temporaryTypesLocal.set(temporaryTypes);
      }

      List<ObjectType> types = Query.from(ObjectType.class).using(database).selectAll();
      int typesSize = types.size();
      LOGGER.info("Loading [{}] types from [{}]", typesSize, database.getName());

      // Load all types from the database first.
      for (ObjectType type : types) {
        type.getFields().size(); // Pre-fetch.
        temporaryTypes.add(type);
      }

      if (initializeClasses) {

        // Make sure that the root type exists.
        ObjectType rootType = getRootType();
        State rootTypeState;

        if (rootType != null) {
          rootTypeState = rootType.getState();

        } else {
          rootType = new ObjectType();
          rootTypeState = rootType.getState();
          rootTypeState.setDatabase(database);
        }

        Map<String, Object> rootTypeOriginals = rootTypeState.getSimpleValues();
        UUID rootTypeId = rootTypeState.getId();
        rootTypeState.setTypeId(rootTypeId);
        rootTypeState.clear();
        rootType.setObjectClassName(ObjectType.class.getName());
        rootType.initialize();
        temporaryTypes.add(rootType);

        try {
          database.beginWrites();

          // Make the new root type available to other types.
          temporaryTypes.add(rootType);
          if (rootTypeState.isNew()) {
            State globals = getGlobals();
            globals.put(ROOT_TYPE_FIELD, rootType);
            globals.save();

          } else if (!rootTypeState.getSimpleValues().equals(rootTypeOriginals)) {
            temporaryTypes.changed.add(rootTypeId);
          }

          Set<Class<? extends Recordable>> objectClasses =
              ClassFinder.findClasses(Recordable.class);

          for (Iterator<Class<? extends Recordable>> i = objectClasses.iterator(); i.hasNext(); ) {
            Class<? extends Recordable> objectClass = i.next();

            try {
              if (objectClass.isAnonymousClass()
                  || Substitution.class.isAssignableFrom(objectClass)) {
                i.remove();
              }

            } catch (IncompatibleClassChangeError error) {
              i.remove();
            }
          }

          Set<Class<?>> globalModifications = new HashSet<Class<?>>();
          Map<ObjectType, List<Class<?>>> typeModifications =
              new HashMap<ObjectType, List<Class<?>>>();

          // Make sure all types are accessible to the rest of the
          // system as soon as possible, so that references can be
          // resolved properly later.
          for (Class<?> objectClass : objectClasses) {
            ObjectType type = getTypeByClass(objectClass);

            if (type == null) {
              type = new ObjectType();
              type.getState().setDatabase(database);

            } else {
              type.getState().clear();
            }

            type.setObjectClassName(objectClass.getName());
            typeModifications.put(type, new ArrayList<Class<?>>());
            temporaryTypes.add(type);
          }

          // Separate out all modifications from regular types.
          for (Class<?> objectClass : objectClasses) {
            if (!Modification.class.isAssignableFrom(objectClass)) {
              continue;
            }

            @SuppressWarnings("unchecked")
            Set<Class<?>> modifiedClasses =
                Modification.Static.getModifiedClasses(
                    (Class<? extends Modification<?>>) objectClass);
            if (modifiedClasses.contains(Object.class)) {
              globalModifications.add(objectClass);
              continue;
            }

            for (Class<?> modifiedClass : modifiedClasses) {
              List<Class<?>> assignableClasses = new ArrayList<Class<?>>();

              for (Class<?> c : objectClasses) {
                if (modifiedClass.isAssignableFrom(c)) {
                  assignableClasses.add(c);
                }
              }

              for (Class<?> assignableClass : assignableClasses) {
                ObjectType type = getTypeByClass(assignableClass);

                if (type != null) {
                  List<Class<?>> modifications = typeModifications.get(type);
                  if (modifications == null) {
                    modifications = new ArrayList<Class<?>>();
                    typeModifications.put(type, modifications);
                  }
                  modifications.add(objectClass);
                }
              }
            }
          }

          // Apply global modifications.
          for (Class<?> modification : globalModifications) {
            ObjectType.modifyAll(database, modification);
          }

          // Initialize all types.
          List<Class<?>> rootTypeModifications = typeModifications.remove(rootType);
          initializeAndModify(temporaryTypes, rootType, rootTypeModifications);

          if (rootTypeModifications != null) {
            for (Class<?> modification : rootTypeModifications) {
              ObjectType t = getTypeByClass(modification);
              initializeAndModify(temporaryTypes, t, typeModifications.remove(t));
            }
          }

          ObjectType fieldType = getTypeByClass(ObjectField.class);
          List<Class<?>> fieldModifications = typeModifications.remove(fieldType);
          initializeAndModify(temporaryTypes, fieldType, fieldModifications);

          if (fieldModifications != null) {
            for (Class<?> modification : fieldModifications) {
              ObjectType t = getTypeByClass(modification);
              initializeAndModify(temporaryTypes, t, typeModifications.remove(t));
            }
          }

          for (Map.Entry<ObjectType, List<Class<?>>> entry : typeModifications.entrySet()) {
            initializeAndModify(temporaryTypes, entry.getKey(), entry.getValue());
          }

          database.commitWrites();

        } finally {
          database.endWrites();
        }
      }

      // Merge temporary types into new permanent types.
      TypesCache newPermanentTypes = new TypesCache();

      for (ObjectType type : permanentTypes.byId.values()) {
        newPermanentTypes.add(type);
      }

      for (ObjectType type : temporaryTypes.byId.values()) {
        newPermanentTypes.add(type);
      }

      newPermanentTypes.changed.addAll(temporaryTypes.changed);
      newPermanentTypes.changed.addAll(permanentTypes.changed);

      // If any types changed, clear all types' extras.
      if (!temporaryTypes.changed.isEmpty()) {
        for (ObjectType type : newPermanentTypes.byId.values()) {
          type.getState().getExtras().clear();
        }
      }

      permanentTypes = newPermanentTypes;
      lastTypesUpdate = new Date();

    } finally {
      temporaryTypesLocal.remove();
    }

    ObjectType singletonType = getTypeByClass(Singleton.class);

    if (singletonType != null) {
      for (ObjectType type : singletonType.findConcreteTypes()) {
        if (!Query.fromType(type).where("_type = ?", type).master().noCache().hasMoreThan(0)) {
          try {
            State.getInstance(type.createObject(null)).saveImmediately();
          } catch (Exception error) {
            LOGGER.warn(String.format("Can't save [%s] singleton!", type.getLabel()), error);
          }
        }
      }
    }

    for (ObjectType type : getTypes()) {
      Class<?> objectClass = type.getObjectClass();
      if (objectClass != null) {
        TypePostProcessorClasses tppcAnnotation =
            objectClass.getAnnotation(TypePostProcessorClasses.class);
        if (tppcAnnotation != null) {
          for (Class<? extends ObjectType.PostProcessor> processorClass : tppcAnnotation.value()) {
            ObjectType.PostProcessor processor =
                (ObjectType.PostProcessor) TYPE_POST_PROCESSORS.getUnchecked(processorClass);
            processor.process(type);
          }
        }
      }
    }
  }
예제 #13
0
파일: Main.java 프로젝트: damorim/pbicc
  public static void main(String[] args) throws Exception {

    init(args[0], args[1]);
    getICCLinkResults();

    DirectedGraph<String, DefaultEdge> g = createDependencyGraph();
    StringBuilder results = new StringBuilder();

    if (ICC_SHOW_INTENT_FILTERS) {
      // TODO we do not need to load manifest if we are not looking at intent filters
      State.getInstance().setManifestParser(new AndroidManifestParser(args[2]));
      StringBuilder localResults = new StringBuilder();
      for (String component : State.getInstance().getManifestParser().intentFilters.keySet()) {
        localResults.append("###\n");
        localResults.append("Component: " + component + "\n");
        localResults.append("Filters:\n");

        for (IntentFilter filter :
            State.getInstance().getManifestParser().intentFilters.get(component)) {
          localResults.append("---\n");
          localResults.append(filter + "\n");
        }
      }
      String toPrint = localResults.toString();
      System.out.println(toPrint);
      results.append(toPrint);
    }

    if (DEBUG_KEYS) {
      StringBuilder localResults = new StringBuilder();
      localResults.append("INTENT KEYS\n");
      for (Map.Entry<String, PutsAndGets> entry : State.getInstance().pgMap().entrySet()) {
        localResults.append(
            String.format(
                "COMP:%s, KEYS:%s\n", entry.getKey().toString(), entry.getValue().toString()));
      }
      String toPrint = localResults.toString();
      System.out.println(toPrint);
      results.append(toPrint);
    }

    IntentStats appIntentStats = new IntentStats();
    ICCLinkFindingResults iccResults = State.getInstance().iccResults();
    if (iccResults.intentsST.getMap().size() > 0) {
      StringBuilder localResults = new StringBuilder();
      // printing the intents
      Map<String, IntentInfo> intents = iccResults.intentsST.getMap();
      IntentInfo info = null;
      for (Map.Entry<String, IntentInfo> intentEntry : intents.entrySet()) {
        info = intentEntry.getValue();
        if ((info.isExplicit() && ICC_SHOW_EXPLICIT_INTENTS)
            || (!info.isExplicit() && ICC_SHOW_IMPLICIT_INTENTS)) {
          localResults.append(
              String.format("%s:\n%s\n----------\n", intentEntry.getKey(), intentEntry.getValue()));
        }
      }

      // printing the vars
      if (ICC_SHOW_VARS) {
        Map<String, VarInfo> vars = iccResults.varsST.getMap();
        for (Map.Entry<String, VarInfo> varEntry : vars.entrySet()) {
          String name = varEntry.getKey();
          VarInfo varInfo = varEntry.getValue();
          localResults.append(String.format("%s %s = %s\n", info.type, name, varInfo.value));
        }
      }

      // printing the links
      if (ICC_SHOW_LINKS) {
        List<ICCLinkInfo<IntentInfo>> links = iccResults.iccLinks;
        for (ICCLinkInfo<IntentInfo> link : links) {
          localResults.append(link + "\n");
        }
      }

      IntentStats stats = iccResults.stats;
      appIntentStats.add(stats);
      if (ICC_SHOW_STATS_PER_FILE) {
        localResults.append(iccResults.stats + "\n");
      }
      String toPrint = localResults.toString();
      System.out.println(toPrint);
      results.append(toPrint);
    }

    if (ICC_SHOW_FINAL_STATS) {
      StringBuilder localResults = new StringBuilder();
      localResults.append("### App Intent Stats\n");
      localResults.append(appIntentStats + "\n");
      localResults.append(appIntentStats.getExtendedAnalysis() + "\n");
      String toPrint = localResults.toString();
      System.out.println(toPrint);
      results.append(toPrint);
    }

    // saving ICC link results information
    if (ICC_SAVE_RESULTS) {
      String toSave = results.toString();
      String name = fileListFile.split("-")[0] + "-icc-results.txt"; // component dependency graph
      BufferedWriter bw = new BufferedWriter(new FileWriter(name));
      bw.write(toSave);
      bw.flush();
      bw.close();
    }

    // saving ICC link results information in JSON format
    if (ICC_SAVE_JSON) {
      String name = fileListFile.split("-")[0] + ".json";
      BufferedWriter bw = new BufferedWriter(new FileWriter(name));
      bw.write(iccResults.toJSON());
      bw.flush();
      bw.close();
    }

    if (PRINT_DOT) {
      String dot = toDot(g);
      String name = fileListFile.split("-")[0] + "-cdg.dot"; // component dependency graph
      BufferedWriter bw = new BufferedWriter(new FileWriter(name));
      bw.write(dot);
      bw.flush();
      bw.close();
    }

    if (PRINT_TOPO_ORDER) {
      System.out.println("TOPO ORDER: ");
      String topoOrder = getTopoOrder(g);
      System.out.println(topoOrder);
      String name = fileListFile.split("-")[0] + "-graph-summary.txt"; // component dependency graph
      BufferedWriter bw = new BufferedWriter(new FileWriter(name));
      bw.write(topoOrder);
      bw.flush();
      bw.close();
    }
  }