private void recordManifestUsages(Node node) { short nodeType = node.getNodeType(); if (nodeType == Node.ELEMENT_NODE) { Element element = (Element) node; NamedNodeMap attributes = element.getAttributes(); for (int i = 0, n = attributes.getLength(); i < n; i++) { Attr attr = (Attr) attributes.item(i); markReachable(getResourceFromUrl(attr.getValue())); } } else if (nodeType == Node.TEXT_NODE) { // Does this apply to any manifests?? String text = node.getNodeValue().trim(); markReachable(getResourceFromUrl(text)); } NodeList children = node.getChildNodes(); for (int i = 0, n = children.getLength(); i < n; i++) { Node child = children.item(i); recordManifestUsages(child); } }
/** Look through text files of unknown structure looking for resource URLs */ private void tokenizeUnknownText(@NonNull String text) { int index = 0; while (index != -1) { index = text.indexOf(ANDROID_RES, index); if (index != -1) { index += ANDROID_RES.length(); // Find the end of the URL int begin = index; int end = begin; int length = text.length(); for (; end < length; end++) { char c = text.charAt(end); if (c != '/' && !Character.isJavaIdentifierPart(c)) { // android_res/raw/my_drawable.png => @raw/my_drawable markReachable(getResourceFromUrl("@" + text.substring(begin, end))); break; } } } } }
+ "matches keep attribute " + value); markReachable(resource); } else if (url.name.contains("*") || url.name.contains("?")) { markReachable(r);
Resource resource = getResourceFromFilePath(string); if (resource != null) { markReachable(resource); continue; } else { + "matches string pool constant " + string); markReachable(resource); + "prefix matches string pool constant " + string); markReachable(resource); + string); markReachable(resource); + "matches string pool constant " + string); markReachable(resource); continue; markReachable(resource); int id = Integer.parseInt(name); if (id != 0) { markReachable(mValueToResource.get(id));
/** Look through binary/unknown files looking for resource URLs */ private void tokenizeUnknownBinary(@NonNull File file) { try { if (sAndroidResBytes == null) { sAndroidResBytes = ANDROID_RES.getBytes(SdkConstants.UTF_8); } byte[] bytes = Files.toByteArray(file); int index = 0; while (index != -1) { index = indexOf(bytes, sAndroidResBytes, index); if (index != -1) { index += sAndroidResBytes.length; // Find the end of the URL int begin = index; int end = begin; for (; end < bytes.length; end++) { byte c = bytes[end]; if (c != '/' && !Character.isJavaIdentifierPart((char)c)) { // android_res/raw/my_drawable.png => @raw/my_drawable String url = "@" + new String(bytes, begin, end - begin, UTF_8); markReachable(getResourceFromUrl(url)); break; } } } } } catch (IOException e) { // Ignore } }
/** * See if the given URL is a URL that we can resolve to a specific resource; if so, * record it and return true, otherwise returns false. */ private boolean referencedUrl(@Nullable Resource from, @NonNull String url) { Resource resource = getResourceFromFilePath(url); if (resource != null) { if (from != null) { from.addReference(resource); } else { // We don't have an inclusion context, so just assume this resource is reachable markReachable(resource); } return true; } return false; }