You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@felix.apache.org by mc...@apache.org on 2011/10/17 12:31:51 UTC
svn commit: r1185095 [14/15] - in /felix/trunk/bundleplugin: ./
src/main/java/aQute/ src/main/java/aQute/bnd/
src/main/java/aQute/bnd/annotation/
src/main/java/aQute/bnd/annotation/component/
src/main/java/aQute/bnd/annotation/metatype/ src/main/java/a...
Added: felix/trunk/bundleplugin/src/main/java/aQute/lib/tag/Tag.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/lib/tag/Tag.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/lib/tag/Tag.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/lib/tag/Tag.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,465 @@
+package aQute.lib.tag;
+
+import java.io.*;
+import java.text.*;
+import java.util.*;
+
+/**
+ * The Tag class represents a minimal XML tree. It consist of a named element
+ * with a hashtable of named attributes. Methods are provided to walk the tree
+ * and get its constituents. The content of a Tag is a list that contains String
+ * objects or other Tag objects.
+ */
+public class Tag {
+ Tag parent; // Parent
+ String name; // Name
+ final Map<String, String> attributes = new LinkedHashMap<String, String>();
+ final List<Object> content = new ArrayList<Object>(); // Content
+ static SimpleDateFormat format = new SimpleDateFormat("yyyyMMddHHmmss.SSS");
+ boolean cdata;
+
+ /**
+ * Construct a new Tag with a name.
+ */
+ public Tag(String name, Object... contents) {
+ this.name = name;
+ for (Object c : contents)
+ content.add(c);
+ }
+
+ public Tag(Tag parent, String name, Object... contents) {
+ this(name,contents);
+ parent.addContent(this);
+ }
+
+ /**
+ * Construct a new Tag with a name.
+ */
+ public Tag(String name, Map<String, String> attributes, Object... contents) {
+ this(name,contents);
+ this.attributes.putAll(attributes);
+
+ }
+ public Tag(String name, Map<String, String> attributes) {
+ this(name, attributes, new Object[0]);
+ }
+
+ /**
+ * Construct a new Tag with a name and a set of attributes. The attributes
+ * are given as ( name, value ) ...
+ */
+ public Tag(String name, String[] attributes, Object... contents) {
+ this(name,contents);
+ for (int i = 0; i < attributes.length; i += 2)
+ addAttribute(attributes[i], attributes[i + 1]);
+ }
+
+ public Tag(String name, String[] attributes) {
+ this(name, attributes, new Object[0]);
+ }
+
+ /**
+ * Add a new attribute.
+ */
+ public Tag addAttribute(String key, String value) {
+ if (value != null)
+ attributes.put(key, value);
+ return this;
+ }
+
+ /**
+ * Add a new attribute.
+ */
+ public Tag addAttribute(String key, Object value) {
+ if (value == null)
+ return this;
+ attributes.put(key, value.toString());
+ return this;
+ }
+
+ /**
+ * Add a new attribute.
+ */
+ public Tag addAttribute(String key, int value) {
+ attributes.put(key, Integer.toString(value));
+ return this;
+ }
+
+ /**
+ * Add a new date attribute. The date is formatted as the SimpleDateFormat
+ * describes at the top of this class.
+ */
+ public Tag addAttribute(String key, Date value) {
+ if (value != null)
+ attributes.put(key, format.format(value));
+ return this;
+ }
+
+ /**
+ * Add a new content string.
+ */
+ public Tag addContent(String string) {
+ if (string != null)
+ content.add(string);
+ return this;
+ }
+
+ /**
+ * Add a new content tag.
+ */
+ public Tag addContent(Tag tag) {
+ content.add(tag);
+ tag.parent = this;
+ return this;
+ }
+
+ /**
+ * Return the name of the tag.
+ */
+ public String getName() {
+ return name;
+ }
+
+ /**
+ * Return the attribute value.
+ */
+ public String getAttribute(String key) {
+ return (String) attributes.get(key);
+ }
+
+ /**
+ * Return the attribute value or a default if not defined.
+ */
+ public String getAttribute(String key, String deflt) {
+ String answer = getAttribute(key);
+ return answer == null ? deflt : answer;
+ }
+
+ /**
+ * Answer the attributes as a Dictionary object.
+ */
+ public Map<String, String> getAttributes() {
+ return attributes;
+ }
+
+ /**
+ * Return the contents.
+ */
+ public List<Object> getContents() {
+ return content;
+ }
+
+ /**
+ * Return a string representation of this Tag and all its children
+ * recursively.
+ */
+ public String toString() {
+ StringWriter sw = new StringWriter();
+ print(0, new PrintWriter(sw));
+ return sw.toString();
+ }
+
+ /**
+ * Return only the tags of the first level of descendants that match the
+ * name.
+ */
+ public List<Object> getContents(String tag) {
+ List<Object> out = new ArrayList<Object>();
+ for (Object o : out) {
+ if (o instanceof Tag && ((Tag) o).getName().equals(tag))
+ out.add(o);
+ }
+ return out;
+ }
+
+ /**
+ * Return the whole contents as a String (no tag info and attributes).
+ */
+ public String getContentsAsString() {
+ StringBuffer sb = new StringBuffer();
+ getContentsAsString(sb);
+ return sb.toString();
+ }
+
+ /**
+ * convenient method to get the contents in a StringBuffer.
+ */
+ public void getContentsAsString(StringBuffer sb) {
+ for (Object o : content) {
+ if (o instanceof Tag)
+ ((Tag) o).getContentsAsString(sb);
+ else
+ sb.append(o.toString());
+ }
+ }
+
+ /**
+ * Print the tag formatted to a PrintWriter.
+ */
+ public Tag print(int indent, PrintWriter pw) {
+ pw.print("\n");
+ spaces(pw, indent);
+ pw.print('<');
+ pw.print(name);
+
+ for (String key : attributes.keySet()) {
+ String value = escape(attributes.get(key));
+ pw.print(' ');
+ pw.print(key);
+ pw.print("=");
+ String quote = "'";
+ if (value.indexOf(quote) >= 0)
+ quote = "\"";
+ pw.print(quote);
+ pw.print(value);
+ pw.print(quote);
+ }
+
+ if (content.size() == 0)
+ pw.print('/');
+ else {
+ pw.print('>');
+ for (Object c : content) {
+ if (c instanceof String) {
+ formatted(pw, indent + 2, 60, escape((String) c));
+ } else if (c instanceof Tag) {
+ Tag tag = (Tag) c;
+ tag.print(indent + 2, pw);
+ }
+ }
+ pw.print("\n");
+ spaces(pw, indent);
+ pw.print("</");
+ pw.print(name);
+ }
+ pw.print('>');
+ return this;
+ }
+
+ /**
+ * Convenience method to print a string nicely and does character conversion
+ * to entities.
+ */
+ void formatted(PrintWriter pw, int left, int width, String s) {
+ int pos = width + 1;
+ s = s.trim();
+
+ for (int i = 0; i < s.length(); i++) {
+ char c = s.charAt(i);
+ if (i == 0 || (Character.isWhitespace(c) && pos > width - 3)) {
+ pw.print("\n");
+ spaces(pw, left);
+ pos = 0;
+ }
+ switch (c) {
+ case '<':
+ pw.print("<");
+ pos += 4;
+ break;
+ case '>':
+ pw.print(">");
+ pos += 4;
+ break;
+ case '&':
+ pw.print("&");
+ pos += 5;
+ break;
+ default:
+ pw.print(c);
+ pos++;
+ break;
+ }
+
+ }
+ }
+
+ /**
+ * Escape a string, do entity conversion.
+ */
+ String escape(String s) {
+ StringBuffer sb = new StringBuffer();
+ for (int i = 0; i < s.length(); i++) {
+ char c = s.charAt(i);
+ switch (c) {
+ case '<':
+ sb.append("<");
+ break;
+ case '>':
+ sb.append(">");
+ break;
+ case '&':
+ sb.append("&");
+ break;
+ default:
+ sb.append(c);
+ break;
+ }
+ }
+ return sb.toString();
+ }
+
+ /**
+ * Make spaces.
+ */
+ void spaces(PrintWriter pw, int n) {
+ while (n-- > 0)
+ pw.print(' ');
+ }
+
+ /**
+ * root/preferences/native/os
+ */
+ public Collection<Tag> select(String path) {
+ return select(path, (Tag) null);
+ }
+
+ public Collection<Tag> select(String path, Tag mapping) {
+ List<Tag> v = new ArrayList<Tag>();
+ select(path, v, mapping);
+ return v;
+ }
+
+ void select(String path, List<Tag> results, Tag mapping) {
+ if (path.startsWith("//")) {
+ int i = path.indexOf('/', 2);
+ String name = path.substring(2, i < 0 ? path.length() : i);
+
+ for (Object o : content) {
+ if (o instanceof Tag) {
+ Tag child = (Tag) o;
+ if (match(name, child, mapping))
+ results.add(child);
+ child.select(path, results, mapping);
+ }
+
+ }
+ return;
+ }
+
+ if (path.length() == 0) {
+ results.add(this);
+ return;
+ }
+
+ int i = path.indexOf("/");
+ String elementName = path;
+ String remainder = "";
+ if (i > 0) {
+ elementName = path.substring(0, i);
+ remainder = path.substring(i + 1);
+ }
+
+ for (Object o : content) {
+ if (o instanceof Tag) {
+ Tag child = (Tag) o;
+ if (child.getName().equals(elementName) || elementName.equals("*"))
+ child.select(remainder, results, mapping);
+ }
+ }
+ }
+
+ public boolean match(String search, Tag child, Tag mapping) {
+ String target = child.getName();
+ String sn = null;
+ String tn = null;
+
+ if (search.equals("*"))
+ return true;
+
+ int s = search.indexOf(':');
+ if (s > 0) {
+ sn = search.substring(0, s);
+ search = search.substring(s + 1);
+ }
+ int t = target.indexOf(':');
+ if (t > 0) {
+ tn = target.substring(0, t);
+ target = target.substring(t + 1);
+ }
+
+ if (!search.equals(target)) // different tag names
+ return false;
+
+ if (mapping == null) {
+ return tn == sn || (sn != null && sn.equals(tn));
+ } else {
+ String suri = sn == null ? mapping.getAttribute("xmlns") : mapping
+ .getAttribute("xmlns:" + sn);
+ String turi = tn == null ? child.findRecursiveAttribute("xmlns") : child
+ .findRecursiveAttribute("xmlns:" + tn);
+ return turi == suri || (turi != null && suri != null && turi.equals(suri));
+ }
+ }
+
+ public String getString(String path) {
+ String attribute = null;
+ int index = path.indexOf("@");
+ if (index >= 0) {
+ // attribute
+ attribute = path.substring(index + 1);
+
+ if (index > 0) {
+ // prefix path
+ path = path.substring(index - 1); // skip -1
+ } else
+ path = "";
+ }
+ Collection<Tag> tags = select(path);
+ StringBuffer sb = new StringBuffer();
+ for (Tag tag : tags) {
+ if (attribute == null)
+ tag.getContentsAsString(sb);
+ else
+ sb.append(tag.getAttribute(attribute));
+ }
+ return sb.toString();
+ }
+
+ public String getStringContent() {
+ StringBuffer sb = new StringBuffer();
+ for (Object c : content) {
+ if (!(c instanceof Tag))
+ sb.append(c);
+ }
+ return sb.toString();
+ }
+
+ public String getNameSpace() {
+ return getNameSpace(name);
+ }
+
+ public String getNameSpace(String name) {
+ int index = name.indexOf(':');
+ if (index > 0) {
+ String ns = name.substring(0, index);
+ return findRecursiveAttribute("xmlns:" + ns);
+ } else
+ return findRecursiveAttribute("xmlns");
+ }
+
+ public String findRecursiveAttribute(String name) {
+ String value = getAttribute(name);
+ if (value != null)
+ return value;
+ if (parent != null)
+ return parent.findRecursiveAttribute(name);
+ return null;
+ }
+
+ public String getLocalName() {
+ int index = name.indexOf(':');
+ if (index <= 0)
+ return name;
+
+ return name.substring(index + 1);
+ }
+
+ public void rename(String string) {
+ name = string;
+ }
+
+ public void setCDATA() {
+ cdata = true;
+ }
+
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/lib/tag/Tag.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/lib/tag/Tag.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/lib/tag/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/lib/tag/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/lib/tag/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/lib/tag/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/command/Command.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/command/Command.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/command/Command.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/command/Command.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,194 @@
+package aQute.libg.command;
+
+import java.io.*;
+import java.util.*;
+import java.util.concurrent.*;
+
+import aQute.libg.reporter.*;
+
+public class Command {
+
+ boolean trace;
+ Reporter reporter;
+ List<String> arguments = new ArrayList<String>();
+ long timeout = 0;
+ File cwd = new File("").getAbsoluteFile();
+ static Timer timer = new Timer();
+ Process process;
+ volatile boolean timedout;
+
+ public int execute(Appendable stdout, Appendable stderr) throws Exception {
+ return execute((InputStream) null, stdout, stderr);
+ }
+
+ public int execute(String input, Appendable stdout, Appendable stderr) throws Exception {
+ InputStream in = new ByteArrayInputStream(input.getBytes("UTF-8"));
+ return execute(in, stdout, stderr);
+ }
+
+ public int execute(InputStream in, Appendable stdout, Appendable stderr) throws Exception {
+ int result;
+ if (reporter != null) {
+ reporter.trace("executing cmd: %s", arguments);
+ }
+
+ String args[] = arguments.toArray(new String[arguments.size()]);
+
+ process = Runtime.getRuntime().exec(args, null, cwd);
+
+ // Make sure the command will not linger when we go
+ Runnable r = new Runnable() {
+ public void run() {
+ process.destroy();
+ }
+ };
+ Thread hook = new Thread(r, arguments.toString());
+ Runtime.getRuntime().addShutdownHook(hook);
+ TimerTask timer = null;
+ OutputStream stdin = process.getOutputStream();
+ final InputStreamHandler handler = in != null ? new InputStreamHandler(in, stdin) : null;
+
+ if (timeout != 0) {
+ timer = new TimerTask() {
+ public void run() {
+ timedout = true;
+ process.destroy();
+ if (handler != null)
+ handler.interrupt();
+ }
+ };
+ Command.timer.schedule(timer, timeout);
+ }
+
+ InputStream out = process.getInputStream();
+ try {
+ InputStream err = process.getErrorStream();
+ try {
+ new Collector(out, stdout).start();
+ new Collector(err, stdout).start();
+ if (handler != null)
+ handler.start();
+
+ result = process.waitFor();
+ } finally {
+ err.close();
+ }
+ } finally {
+ out.close();
+ if (timer != null)
+ timer.cancel();
+ Runtime.getRuntime().removeShutdownHook(hook);
+ if (handler != null)
+ handler.interrupt();
+ }
+ if (reporter != null)
+ reporter.trace("cmd %s executed with result=%d, result: %s/%s", arguments, result,
+ stdout, stderr);
+
+ if( timedout )
+ return Integer.MIN_VALUE;
+ byte exitValue = (byte) process.exitValue();
+ return exitValue;
+ }
+
+ public void add(String... args) {
+ for (String arg : args)
+ arguments.add(arg);
+ }
+
+ public void addAll(Collection<String> args) {
+ arguments.addAll(args);
+ }
+
+ public void setTimeout(long duration, TimeUnit unit) {
+ timeout = unit.toMillis(duration);
+ }
+
+ public void setTrace() {
+ this.trace = true;
+ }
+
+ public void setReporter(Reporter reporter) {
+ this.reporter = reporter;
+ }
+
+ public void setCwd(File dir) {
+ if (!dir.isDirectory())
+ throw new IllegalArgumentException("Working directory must be a directory: " + dir);
+
+ this.cwd = dir;
+ }
+
+ public void cancel() {
+ process.destroy();
+ }
+
+ class Collector extends Thread {
+ final InputStream in;
+ final Appendable sb;
+
+ public Collector(InputStream inputStream, Appendable sb) {
+ this.in = inputStream;
+ this.sb = sb;
+ }
+
+ public void run() {
+ try {
+ int c = in.read();
+ while (c >= 0) {
+ if (trace)
+ System.out.print((char) c);
+ sb.append((char) c);
+ c = in.read();
+ }
+ } catch (Exception e) {
+ try {
+ sb.append("\n**************************************\n");
+ sb.append(e.toString());
+ sb.append("\n**************************************\n");
+ } catch (IOException e1) {
+ }
+ if (reporter != null) {
+ reporter.trace("cmd exec: %s", e);
+ }
+ }
+ }
+ }
+
+ class InputStreamHandler extends Thread {
+ final InputStream in;
+ final OutputStream stdin;
+
+ public InputStreamHandler(InputStream in, OutputStream stdin) {
+ this.stdin = stdin;
+ this.in = in;
+ }
+
+ public void run() {
+ try {
+ int c = in.read();
+ while (c >= 0) {
+ stdin.write(c);
+ stdin.flush();
+ c = in.read();
+ }
+ } catch (InterruptedIOException e) {
+ // Ignore here
+ } catch (Exception e) {
+ // Who cares?
+ }
+ }
+ }
+
+ public String toString() {
+ StringBuilder sb = new StringBuilder();
+ String del = "";
+
+ for (String argument : arguments) {
+ sb.append(del);
+ sb.append(argument);
+ del = " ";
+ }
+ return sb.toString();
+ }
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/command/Command.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/command/Command.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/command/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/command/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/command/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/command/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Crypto.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Crypto.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Crypto.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Crypto.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,67 @@
+package aQute.libg.cryptography;
+
+import java.math.*;
+import java.security.*;
+import java.security.interfaces.*;
+import java.security.spec.*;
+import java.util.regex.*;
+
+public class Crypto {
+ static final Pattern RSA_PRIVATE = Pattern
+ .compile("\\s*RSA.Private\\((\\p{xDigit})+:(\\p{xDigit})+\\)\\s*");
+ static final Pattern RSA_PUBLIC = Pattern
+ .compile("\\s*RSA.Public\\((\\p{xDigit})+:(\\p{xDigit})+\\)\\s*");
+
+ /**
+ *
+ * @param <T>
+ * @param spec
+ * @return
+ * @throws Exception
+ */
+ @SuppressWarnings("unchecked") public static <T> T fromString(String spec, Class<T> c) throws Exception {
+ if ( PrivateKey.class.isAssignableFrom(c)) {
+ Matcher m = RSA_PRIVATE.matcher(spec);
+ if ( m.matches()) {
+ return (T) RSA.createPrivate(
+ new BigInteger(m.group(1)), new BigInteger(m.group(2)));
+ }
+ throw new IllegalArgumentException("No such private key " + spec );
+ }
+
+ if ( PublicKey.class.isAssignableFrom(c)) {
+ Matcher m = RSA_PUBLIC.matcher(spec);
+ if ( m.matches()) {
+ return (T) RSA.create( new RSAPublicKeySpec(
+ new BigInteger(m.group(1)), new BigInteger(m.group(2))));
+ }
+ throw new IllegalArgumentException("No such public key " + spec );
+ }
+ return null;
+ }
+
+ public static String toString( Object key ) {
+ if ( key instanceof RSAPrivateKey ) {
+ RSAPrivateKey pk = (RSAPrivateKey) key;
+ return "RSA.Private(" + pk.getModulus() + ":" + pk.getPrivateExponent() + ")";
+ }
+ if ( key instanceof RSAPublicKey ) {
+ RSAPublicKey pk = (RSAPublicKey) key;
+ return "RSA.Private(" + pk.getModulus() + ":" + pk.getPublicExponent() + ")";
+ }
+ return null;
+ }
+
+
+ public static <T extends Digest> Signer<T> signer(PrivateKey key, Digester<T> digester) throws NoSuchAlgorithmException {
+ Signature s = Signature.getInstance(key.getAlgorithm() + "with" + digester.getAlgorithm());
+ return new Signer<T>(s,digester);
+ }
+
+ public static Verifier verifier(PublicKey key, Digest digest) throws NoSuchAlgorithmException {
+ Signature s = Signature.getInstance(key.getAlgorithm() + "with" + digest.getAlgorithm());
+ return new Verifier(s,digest);
+ }
+
+
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Crypto.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Crypto.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Digest.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Digest.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Digest.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Digest.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,25 @@
+package aQute.libg.cryptography;
+
+import aQute.lib.hex.*;
+
+public abstract class Digest {
+ final byte[] digest;
+
+ protected Digest(byte[] checksum, int width) {
+ this.digest = checksum;
+ if (digest.length != width)
+ throw new IllegalArgumentException("Invalid width for digest: " + digest.length
+ + " expected " + width);
+ }
+
+
+ public byte[] digest() {
+ return digest;
+ }
+
+ @Override public String toString() {
+ return String.format("%s(d=%s)", getAlgorithm(), Hex.toHexString(digest));
+ }
+
+ public abstract String getAlgorithm();
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Digest.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Digest.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Digester.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Digester.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Digester.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Digester.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,35 @@
+package aQute.libg.cryptography;
+
+import java.io.*;
+import java.security.*;
+
+import aQute.lib.io.*;
+
+public abstract class Digester<T extends Digest> extends OutputStream {
+ protected MessageDigest md;
+
+ public Digester(MessageDigest instance){
+ md = instance;
+ }
+ @Override
+ public void write( byte[] buffer, int offset, int length) throws IOException{
+ md.update(buffer,offset,length);
+ }
+ @Override
+ public void write( int b) throws IOException{
+ md.update((byte) b);
+ }
+
+ public MessageDigest getMessageDigest() throws Exception {
+ return md;
+ }
+
+ public T from(InputStream in) throws Exception {
+ IO.copy(in,this);
+ return digest();
+ }
+
+ public abstract T digest() throws Exception;
+ public abstract T digest( byte [] bytes) throws Exception;
+ public abstract String getAlgorithm();
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Digester.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Digester.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Key.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Key.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Key.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Key.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,8 @@
+package aQute.libg.cryptography;
+
+
+public abstract class Key implements java.security.Key {
+ private static final long serialVersionUID = 1L;
+
+
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Key.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Key.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/MD5.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/MD5.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/MD5.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/MD5.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,33 @@
+package aQute.libg.cryptography;
+
+import java.security.*;
+
+
+
+public class MD5 extends Digest {
+ public final static String ALGORITHM = "MD5";
+
+ public static Digester<MD5> getDigester() throws Exception {
+ return new Digester<MD5>(MessageDigest.getInstance(ALGORITHM)) {
+
+ @Override public MD5 digest() throws Exception {
+ return new MD5(md.digest());
+ }
+
+ @Override public MD5 digest(byte[] bytes) {
+ return new MD5(bytes);
+ }
+ @Override public String getAlgorithm() {
+ return ALGORITHM;
+ }
+ };
+ }
+
+
+ public MD5(byte[] digest) {
+ super(digest,16);
+ }
+
+ @Override public String getAlgorithm() { return ALGORITHM; }
+
+}
\ No newline at end of file
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/MD5.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/MD5.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/RSA.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/RSA.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/RSA.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/RSA.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,43 @@
+package aQute.libg.cryptography;
+
+import java.math.*;
+import java.security.*;
+import java.security.interfaces.*;
+import java.security.spec.*;
+
+import aQute.libg.tuple.*;
+
+public class RSA {
+ final static String ALGORITHM = "RSA";
+
+ final static KeyFactory factory = getKeyFactory();
+
+ static private KeyFactory getKeyFactory() {
+ try {
+ return KeyFactory.getInstance(ALGORITHM);
+ } catch (Exception e) {
+ // built in
+ }
+ return null;
+ }
+
+ public static RSAPrivateKey create(RSAPrivateKeySpec keyspec) throws InvalidKeySpecException {
+ return (RSAPrivateKey) factory.generatePrivate(keyspec);
+ }
+ public static RSAPublicKey create(RSAPublicKeySpec keyspec) throws InvalidKeySpecException {
+ return (RSAPublicKey) factory.generatePrivate(keyspec);
+ }
+
+ public static RSAPublicKey createPublic(BigInteger m, BigInteger e) throws InvalidKeySpecException {
+ return create( new RSAPublicKeySpec(m,e));
+ }
+ public static RSAPrivateKey createPrivate(BigInteger m, BigInteger e) throws InvalidKeySpecException {
+ return create( new RSAPrivateKeySpec(m,e));
+ }
+
+ public static Pair<RSAPrivateKey, RSAPublicKey> generate() throws NoSuchAlgorithmException {
+ KeyPairGenerator kpg = KeyPairGenerator.getInstance(ALGORITHM);
+ KeyPair keypair = kpg.generateKeyPair();
+ return new Pair<RSAPrivateKey,RSAPublicKey>( (RSAPrivateKey) keypair.getPrivate(), (RSAPublicKey) keypair.getPublic());
+ }
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/RSA.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/RSA.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/SHA1.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/SHA1.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/SHA1.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/SHA1.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,33 @@
+package aQute.libg.cryptography;
+
+import java.security.*;
+
+
+
+public class SHA1 extends Digest {
+ public final static String ALGORITHM = "SHA1";
+
+ public static Digester<SHA1> getDigester() throws NoSuchAlgorithmException {
+ MessageDigest md = MessageDigest.getInstance(ALGORITHM);
+ return new Digester<SHA1>(md) {
+ @Override public SHA1 digest() throws Exception {
+ return new SHA1(md.digest());
+ }
+
+ @Override public SHA1 digest(byte[] bytes) {
+ return new SHA1(bytes);
+ }
+ @Override public String getAlgorithm() {
+ return ALGORITHM;
+ }
+ };
+ }
+
+ public SHA1(byte[] b) {
+ super(b, 20);
+ }
+
+
+ @Override public String getAlgorithm() { return ALGORITHM; }
+
+}
\ No newline at end of file
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/SHA1.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/SHA1.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Signer.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Signer.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Signer.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Signer.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,35 @@
+package aQute.libg.cryptography;
+
+import java.io.*;
+import java.security.*;
+
+public class Signer<D extends Digest> extends OutputStream {
+ Signature signature;
+ Digester<D> digester;
+
+ Signer(Signature s, Digester<D> digester) {
+ this.signature = s;
+ this.digester = digester;
+ }
+
+ @Override public void write(byte[] buffer, int offset, int length) throws IOException {
+ try {
+ signature.update(buffer, offset, length);
+ } catch (SignatureException e) {
+ throw new IOException(e);
+ }
+ }
+
+ @Override public void write(int b) throws IOException {
+ try {
+ signature.update((byte) b);
+ } catch (SignatureException e) {
+ throw new IOException(e);
+ }
+ }
+
+
+ public D signature() throws Exception {
+ return digester.digest(signature().digest());
+ }
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Signer.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Signer.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Verifier.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Verifier.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Verifier.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Verifier.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,38 @@
+package aQute.libg.cryptography;
+
+import java.io.*;
+import java.security.*;
+
+
+public class Verifier extends OutputStream {
+ final Signature signature;
+ final Digest d;
+
+ Verifier(Signature s, Digest d) {
+ this.signature = s;
+ this.d = d;
+ }
+
+ @Override
+ public void write( byte[] buffer, int offset, int length) throws IOException {
+ try {
+ signature.update(buffer, offset, length);
+ } catch (SignatureException e) {
+ throw new IOException(e);
+ }
+ }
+
+ @Override
+ public void write( int b) throws IOException {
+ try {
+ signature.update((byte) b);
+ } catch (SignatureException e) {
+ throw new IOException(e);
+ }
+ }
+
+ public boolean verify() throws Exception {
+ return signature.verify(d.digest());
+ }
+
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Verifier.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/Verifier.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/cryptography/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/fileiterator/FileIterator.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/fileiterator/FileIterator.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/fileiterator/FileIterator.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/fileiterator/FileIterator.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,45 @@
+package aQute.libg.fileiterator;
+
+import java.io.*;
+import java.util.*;
+
+public class FileIterator implements Iterator<File> {
+ File dir;
+ int n = 0;
+ FileIterator next;
+
+ public FileIterator(File nxt) {
+ assert nxt.isDirectory();
+ this.dir = nxt;
+ }
+
+ public boolean hasNext() {
+ if (next != null)
+ return next.hasNext();
+ else
+ return n < dir.list().length;
+ }
+
+ public File next() {
+ if (next != null) {
+ File answer = next.next();
+ if (!next.hasNext())
+ next = null;
+ return answer;
+ } else {
+ File nxt = dir.listFiles()[n++];
+ if (nxt.isDirectory()) {
+ next = new FileIterator(nxt);
+ return nxt;
+ } else if (nxt.isFile()) {
+ return nxt;
+ } else
+ throw new IllegalStateException("File disappeared");
+ }
+ }
+
+ public void remove() {
+ throw new UnsupportedOperationException(
+ "Cannot remove from a file iterator");
+ }
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/fileiterator/FileIterator.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/fileiterator/FileIterator.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/fileiterator/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/fileiterator/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/fileiterator/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/fileiterator/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/filelock/DirectoryLock.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/filelock/DirectoryLock.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/filelock/DirectoryLock.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/filelock/DirectoryLock.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,32 @@
+package aQute.libg.filelock;
+
+import java.io.*;
+
+public class DirectoryLock {
+ final File lock;
+ final long timeout;
+ final public static String LOCKNAME = ".lock";
+
+ public DirectoryLock(File directory, long timeout) {
+ this.lock = new File(directory, LOCKNAME);
+ this.lock.deleteOnExit();
+ this.timeout = timeout;
+ }
+
+
+ public void release() {
+ lock.delete();
+ }
+
+ public void lock() throws InterruptedException {
+ if (lock.mkdir())
+ return;
+
+ long deadline = System.currentTimeMillis()+ timeout;
+ while ( System.currentTimeMillis() < deadline) {
+ if (lock.mkdir())
+ return;
+ Thread.sleep(50);
+ }
+ }
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/filelock/DirectoryLock.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/filelock/DirectoryLock.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/forker/Forker.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/forker/Forker.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/forker/Forker.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/forker/Forker.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,184 @@
+package aQute.libg.forker;
+
+import java.util.*;
+import java.util.concurrent.*;
+import java.util.concurrent.atomic.*;
+
+/**
+ * A Forker is good in parallel scheduling tasks with dependencies. You can add
+ * tasks with {@link #doWhen(Collection, Object, Runnable)}. The collection is
+ * the list of dependencies, the object is the target, and the runnable is run
+ * to update the target. The runnable will only run when all its dependencies
+ * have ran their associated runnable.
+ *
+ * @author aqute
+ *
+ * @param <T>
+ */
+public class Forker<T> {
+ final Executor executor;
+ final Set<T> done = new HashSet<T>();
+ final List<Job> waiting = new ArrayList<Job>();
+ final Semaphore semaphore = new Semaphore(0);
+ final AtomicInteger outstanding = new AtomicInteger();
+ final AtomicBoolean canceled = new AtomicBoolean();
+
+ /**
+ * Helper class to model a Job
+ */
+ class Job implements Runnable {
+ T target;
+ Set<T> dependencies;
+ Runnable runnable;
+ Throwable exception;
+ volatile Thread t;
+ volatile AtomicBoolean canceled = new AtomicBoolean(false);
+
+ /**
+ * Run when the job's dependencies are done.
+ */
+ public void run() {
+ Thread.interrupted(); // clear the interrupt flag
+
+ try {
+ synchronized (this) {
+ // Check if we got canceled
+ if (canceled.get())
+ return;
+
+ t = Thread.currentThread();
+ }
+ runnable.run();
+ } catch (Exception e) {
+ exception = e;
+ } finally {
+ synchronized (this) {
+ t = null;
+ }
+ Thread.interrupted(); // clear the interrupt flag
+ done(target);
+ }
+ }
+
+ /**
+ * Cancel this job
+ */
+ private void cancel() {
+ if (!canceled.getAndSet(true)) {
+ synchronized (this) {
+ if (t != null)
+ t.interrupt();
+ }
+ }
+ }
+ }
+
+ /**
+ * Constructor
+ *
+ * @param executor
+ */
+ public Forker(Executor executor) {
+ this.executor = executor;
+ }
+
+ /**
+ * Constructor
+ *
+ */
+ public Forker() {
+ this.executor = Executors.newFixedThreadPool(4);
+ }
+
+ /**
+ * Schedule a job for execution when the dependencies are done of target are
+ * done.
+ *
+ * @param dependencies the dependencies that must have run
+ * @param target the target, is removed from all the dependencies when it ran
+ * @param runnable the runnable to run
+ */
+ public synchronized void doWhen(Collection<? extends T> dependencies, T target,
+ Runnable runnable) {
+ System.out.println("doWhen " + dependencies);
+ outstanding.incrementAndGet();
+ Job job = new Job();
+ job.dependencies = new HashSet<T>(dependencies);
+ job.dependencies.removeAll(done);
+ job.target = target;
+
+ job.runnable = runnable;
+ if (job.dependencies.isEmpty()) {
+ executor.execute(job);
+ } else {
+ waiting.add(job);
+ }
+ }
+
+ /**
+ * Called when the target has ran by the Job.
+ *
+ * @param done
+ */
+ private void done(T done) {
+ List<Runnable> torun = new ArrayList<Runnable>();
+ synchronized (this) {
+ System.out.println("done " + done);
+ semaphore.release();
+
+ for (Iterator<Job> e = waiting.iterator(); e.hasNext();) {
+ Job job = e.next();
+ if (job.dependencies.remove(done) && job.dependencies.isEmpty()) {
+ System.out.println("scheduling " + job.target);
+ torun.add(job);
+ e.remove();
+ }
+ }
+ }
+ for (Runnable r : torun)
+ executor.execute(r);
+ }
+
+ /**
+ * Wait until all jobs have run.
+ *
+ * @throws InterruptedException
+ */
+ public void join() throws InterruptedException {
+ System.out.println("join " + outstanding + " " + semaphore);
+ check();
+ semaphore.acquire(outstanding.getAndSet(0));
+ }
+
+ /**
+ * Check that we have no jobs that can never be satisfied. I.e. if
+ * the dependencies contain a target that is not listed.
+ */
+ private void check() {
+ // TODO
+ }
+
+ /**
+ * Return the number of outstanding jobs
+ * @return outstanding jobs
+ */
+ public int getOutstanding() {
+ return semaphore.availablePermits();
+ }
+
+ /**
+ * Cancel the forker.
+ *
+ * @throws InterruptedException
+ */
+ public void cancel() throws InterruptedException {
+ System.out.println("canceled " + outstanding + " " + semaphore);
+
+ if (!canceled.getAndSet(true)) {
+ for (Job job : waiting) {
+ job.cancel();
+ }
+ }
+ join();
+ }
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/forker/Forker.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/forker/Forker.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/forker/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/forker/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/forker/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/forker/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/generics/Create.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/generics/Create.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/generics/Create.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/generics/Create.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,42 @@
+package aQute.libg.generics;
+
+import java.util.*;
+
+public class Create {
+
+ public static <K,V> Map<K, V> map() {
+ return new LinkedHashMap<K,V>();
+ }
+
+ public static <T> List<T> list() {
+ return new ArrayList<T>();
+ }
+
+ public static <T> Set<T> set() {
+ return new HashSet<T>();
+ }
+
+ public static <T> List<T> list(T[] source) {
+ return new ArrayList<T>(Arrays.asList(source));
+ }
+
+ public static <T> Set<T> set(T[]source) {
+ return new HashSet<T>(Arrays.asList(source));
+ }
+
+ public static <K,V> Map<K, V> copy(Map<K,V> source) {
+ return new LinkedHashMap<K,V>(source);
+ }
+
+ public static <T> List<T> copy(List<T> source) {
+ return new ArrayList<T>(source);
+ }
+
+ public static <T> Set<T> copy(Collection<T> source) {
+ if ( source == null )
+ return set();
+ return new HashSet<T>(source);
+ }
+
+
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/generics/Create.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/generics/Create.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/generics/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/generics/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/generics/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/generics/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/header/OSGiHeader.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/header/OSGiHeader.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/header/OSGiHeader.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/header/OSGiHeader.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,145 @@
+package aQute.libg.header;
+
+import java.util.*;
+
+import aQute.libg.generics.*;
+import aQute.libg.qtokens.*;
+import aQute.libg.reporter.*;
+
+public class OSGiHeader {
+
+ static public Map<String, Map<String, String>> parseHeader(String value) {
+ return parseHeader(value, null);
+ }
+
+ /**
+ * Standard OSGi header parser. This parser can handle the format clauses
+ * ::= clause ( ',' clause ) + clause ::= name ( ';' name ) (';' key '='
+ * value )
+ *
+ * This is mapped to a Map { name => Map { attr|directive => value } }
+ *
+ * @param value
+ * A string
+ * @return a Map<String,Map<String,String>>
+ */
+ static public Map<String, Map<String, String>> parseHeader(String value,
+ Reporter logger) {
+ if (value == null || value.trim().length() == 0)
+ return Create.map();
+
+ Map<String, Map<String, String>> result = Create.map();
+ QuotedTokenizer qt = new QuotedTokenizer(value, ";=,");
+ char del = 0;
+ do {
+ boolean hadAttribute = false;
+ Map<String, String> clause = Create.map();
+ List<String> aliases = Create.list();
+ String name = qt.nextToken(",;");
+
+ del = qt.getSeparator();
+ if (name == null || name.length() == 0) {
+ if (logger != null && logger.isPedantic()) {
+ logger
+ .warning("Empty clause, usually caused by repeating a comma without any name field or by having spaces after the backslash of a property file: "
+ + value);
+ }
+ if (name == null)
+ break;
+ } else {
+ name = name.trim();
+
+ aliases.add(name);
+ while (del == ';') {
+ String adname = qt.nextToken();
+ if ((del = qt.getSeparator()) != '=') {
+ if (hadAttribute)
+ if (logger != null) {
+ logger
+ .error("Header contains name field after attribute or directive: "
+ + adname
+ + " from "
+ + value
+ + ". Name fields must be consecutive, separated by a ';' like a;b;c;x=3;y=4");
+ }
+ if (adname != null && adname.length() > 0)
+ aliases.add(adname.trim());
+ } else {
+ String advalue = qt.nextToken();
+ if (clause.containsKey(adname)) {
+ if (logger != null && logger.isPedantic())
+ logger
+ .warning("Duplicate attribute/directive name "
+ + adname
+ + " in "
+ + value
+ + ". This attribute/directive will be ignored");
+ }
+ if (advalue == null) {
+ if (logger != null)
+ logger
+ .error("No value after '=' sign for attribute "
+ + adname);
+ advalue = "";
+ }
+ clause.put(adname.trim(), advalue.trim());
+ del = qt.getSeparator();
+ hadAttribute = true;
+ }
+ }
+
+ // Check for duplicate names. The aliases list contains
+ // the list of nams, for each check if it exists. If so,
+ // add a number of "~" to make it unique.
+ for (String clauseName : aliases) {
+ if (result.containsKey(clauseName)) {
+ if (logger != null && logger.isPedantic())
+ logger
+ .warning("Duplicate name "
+ + clauseName
+ + " used in header: '"
+ + clauseName
+ + "'. Duplicate names are specially marked in Bnd with a ~ at the end (which is stripped at printing time).");
+ while (result.containsKey(clauseName))
+ clauseName += "~";
+ }
+ result.put(clauseName, clause);
+ }
+ }
+ } while (del == ',');
+ return result;
+ }
+
+ public static Map<String, String> parseProperties(String input) {
+ return parseProperties(input, null);
+ }
+
+ public static Map<String, String> parseProperties(String input, Reporter logger) {
+ if (input == null || input.trim().length() == 0)
+ return Create.map();
+
+ Map<String, String> result = Create.map();
+ QuotedTokenizer qt = new QuotedTokenizer(input, "=,");
+ char del = ',';
+
+ while (del == ',') {
+ String key = qt.nextToken(",=");
+ String value = "";
+ del = qt.getSeparator();
+ if (del == '=') {
+ value = qt.nextToken(",=");
+ del = qt.getSeparator();
+ }
+ result.put(key, value);
+ }
+ if (del != 0)
+ if ( logger == null )
+ throw new IllegalArgumentException(
+ "Invalid syntax for properties: " + input);
+ else
+ logger.error("Invalid syntax for properties: " + input);
+
+ return result;
+ }
+
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/header/OSGiHeader.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/header/OSGiHeader.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/header/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/header/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/header/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/header/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/qtokens/QuotedTokenizer.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/qtokens/QuotedTokenizer.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/qtokens/QuotedTokenizer.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/qtokens/QuotedTokenizer.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,118 @@
+package aQute.libg.qtokens;
+
+import java.util.*;
+
+import aQute.libg.generics.*;
+
+public class QuotedTokenizer {
+ String string;
+ int index = 0;
+ String separators;
+ boolean returnTokens;
+ boolean ignoreWhiteSpace = true;
+ String peek;
+ char separator;
+
+ public QuotedTokenizer(String string, String separators, boolean returnTokens ) {
+ if ( string == null )
+ throw new IllegalArgumentException("string argument must be not null");
+ this.string = string;
+ this.separators = separators;
+ this.returnTokens = returnTokens;
+ }
+ public QuotedTokenizer(String string, String separators) {
+ this(string,separators,false);
+ }
+
+ public String nextToken(String separators) {
+ separator = 0;
+ if ( peek != null ) {
+ String tmp = peek;
+ peek = null;
+ return tmp;
+ }
+
+ if ( index == string.length())
+ return null;
+
+ StringBuffer sb = new StringBuffer();
+
+ while (index < string.length()) {
+ char c = string.charAt(index++);
+
+ if ( Character.isWhitespace(c)) {
+ if ( index == string.length())
+ break;
+ else {
+ sb.append(c);
+ continue;
+ }
+ }
+
+ if (separators.indexOf(c) >= 0) {
+ if (returnTokens)
+ peek = Character.toString(c);
+ else
+ separator = c;
+ break;
+ }
+
+ switch (c) {
+ case '"' :
+ case '\'' :
+ quotedString(sb, c);
+ break;
+
+ default :
+ sb.append(c);
+ }
+ }
+ String result = sb.toString().trim();
+ if ( result.length()==0 && index==string.length())
+ return null;
+ return result;
+ }
+
+ public String nextToken() {
+ return nextToken(separators);
+ }
+
+ private void quotedString(StringBuffer sb, char c) {
+ char quote = c;
+ while (index < string.length()) {
+ c = string.charAt(index++);
+ if (c == quote)
+ break;
+ if (c == '\\' && index < string.length()
+ && string.charAt(index + 1) == quote)
+ c = string.charAt(index++);
+ sb.append(c);
+ }
+ }
+
+ public String[] getTokens() {
+ return getTokens(0);
+ }
+
+ private String [] getTokens(int cnt){
+ String token = nextToken();
+ if ( token == null )
+ return new String[cnt];
+
+ String result[] = getTokens(cnt+1);
+ result[cnt]=token;
+ return result;
+ }
+
+ public char getSeparator() { return separator; }
+
+ public List<String> getTokenSet() {
+ List<String> list = Create.list();
+ String token = nextToken();
+ while ( token != null ) {
+ list.add(token);
+ token = nextToken();
+ }
+ return list;
+ }
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/qtokens/QuotedTokenizer.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/qtokens/QuotedTokenizer.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/qtokens/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/qtokens/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/qtokens/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/qtokens/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/reporter/Reporter.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/reporter/Reporter.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/reporter/Reporter.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/reporter/Reporter.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,15 @@
+package aQute.libg.reporter;
+
+import java.util.*;
+
+
+public interface Reporter {
+ void error(String s, Object ... args);
+ void warning(String s, Object ... args);
+ void progress(String s, Object ... args);
+ void trace(String s, Object ... args);
+ List<String> getWarnings();
+ List<String> getErrors();
+
+ boolean isPedantic();
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/reporter/Reporter.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/reporter/Reporter.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/reporter/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/reporter/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/reporter/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/reporter/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/ContentFilter.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/ContentFilter.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/ContentFilter.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/ContentFilter.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,8 @@
+package aQute.libg.sax;
+
+import org.xml.sax.ContentHandler;
+
+public interface ContentFilter extends ContentHandler {
+ void setParent(ContentHandler parent);
+ ContentHandler getParent();
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/ContentFilter.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/ContentFilter.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/ContentFilterImpl.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/ContentFilterImpl.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/ContentFilterImpl.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/ContentFilterImpl.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,71 @@
+package aQute.libg.sax;
+
+import org.xml.sax.Attributes;
+import org.xml.sax.ContentHandler;
+import org.xml.sax.Locator;
+import org.xml.sax.SAXException;
+
+public class ContentFilterImpl implements ContentFilter {
+
+ private ContentHandler parent;
+
+ public void setParent(ContentHandler parent) {
+ this.parent = parent;
+
+ }
+
+ public ContentHandler getParent() {
+ return parent;
+ }
+
+ public void setDocumentLocator(Locator locator) {
+ parent.setDocumentLocator(locator);
+ }
+
+ public void startDocument() throws SAXException {
+ parent.startDocument();
+ }
+
+ public void endDocument() throws SAXException {
+ parent.endDocument();
+ }
+
+ public void startPrefixMapping(String prefix, String uri)
+ throws SAXException {
+ parent.startPrefixMapping(prefix, uri);
+ }
+
+ public void endPrefixMapping(String prefix) throws SAXException {
+ parent.endPrefixMapping(prefix);
+ }
+
+ public void startElement(String uri, String localName, String qName,
+ Attributes atts) throws SAXException {
+ parent.startElement(uri, localName, qName, atts);
+ }
+
+ public void endElement(String uri, String localName, String qName)
+ throws SAXException {
+ parent.endElement(uri, localName, qName);
+ }
+
+ public void characters(char[] ch, int start, int length)
+ throws SAXException {
+ parent.characters(ch, start, length);
+ }
+
+ public void ignorableWhitespace(char[] ch, int start, int length)
+ throws SAXException {
+ parent.ignorableWhitespace(ch, start, length);
+ }
+
+ public void processingInstruction(String target, String data)
+ throws SAXException {
+ parent.processingInstruction(target, data);
+ }
+
+ public void skippedEntity(String name) throws SAXException {
+ parent.skippedEntity(name);
+ }
+
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/ContentFilterImpl.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/ContentFilterImpl.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/SAXElement.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/SAXElement.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/SAXElement.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/SAXElement.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,36 @@
+package aQute.libg.sax;
+
+import org.xml.sax.Attributes;
+
+public class SAXElement {
+
+ private final String uri;
+ private final String localName;
+ private final String qName;
+ private final Attributes atts;
+
+ public SAXElement(String uri, String localName, String qName,
+ Attributes atts) {
+ this.uri = uri;
+ this.localName = localName;
+ this.qName = qName;
+ this.atts = atts;
+ }
+
+ public String getUri() {
+ return uri;
+ }
+
+ public String getLocalName() {
+ return localName;
+ }
+
+ public String getqName() {
+ return qName;
+ }
+
+ public Attributes getAtts() {
+ return atts;
+ }
+
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/SAXElement.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/SAXElement.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/SAXUtil.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/SAXUtil.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/SAXUtil.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/SAXUtil.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,29 @@
+package aQute.libg.sax;
+
+import javax.xml.parsers.SAXParserFactory;
+import javax.xml.transform.Result;
+import javax.xml.transform.sax.SAXTransformerFactory;
+import javax.xml.transform.sax.TransformerHandler;
+
+import org.xml.sax.ContentHandler;
+import org.xml.sax.XMLReader;
+
+public class SAXUtil {
+
+ public static XMLReader buildPipeline(Result output, ContentFilter... filters) throws Exception {
+ SAXTransformerFactory factory = (SAXTransformerFactory) SAXTransformerFactory.newInstance();
+ TransformerHandler handler = factory.newTransformerHandler();
+ handler.setResult(output);
+
+ ContentHandler last = handler;
+ if (filters != null) for (ContentFilter filter : filters) {
+ filter.setParent(last);
+ last = filter;
+ }
+ XMLReader reader = SAXParserFactory.newInstance().newSAXParser().getXMLReader();
+ reader.setContentHandler(last);
+
+ return reader;
+ }
+
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/SAXUtil.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/SAXUtil.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/ElementSelectionFilter.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/ElementSelectionFilter.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/ElementSelectionFilter.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/ElementSelectionFilter.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,49 @@
+package aQute.libg.sax.filters;
+
+import org.xml.sax.Attributes;
+import org.xml.sax.SAXException;
+
+import aQute.libg.sax.ContentFilterImpl;
+
+public abstract class ElementSelectionFilter extends ContentFilterImpl{
+
+ int depth = 0;
+ int hiddenDepth = -1;
+
+ protected abstract boolean select(int depth, String uri, String localName, String qName, Attributes attribs);
+
+ @Override
+ public final void startElement(String uri, String localName, String qName, Attributes atts) throws SAXException {
+ if (hiddenDepth < 0) {
+ boolean allow = select(depth, uri, localName, qName, atts);
+ if (allow)
+ super.startElement(uri, localName, qName, atts);
+ else
+ hiddenDepth = 0;
+ } else {
+ hiddenDepth ++;
+ }
+ depth++;
+ }
+
+ @Override
+ public final void endElement(String uri, String localName, String qName) throws SAXException {
+ if (hiddenDepth < 0) {
+ super.endElement(uri, localName, qName);
+ } else {
+ hiddenDepth --;
+ }
+ depth --;
+ }
+
+ @Override
+ public void characters(char[] ch, int start, int length) throws SAXException {
+ if (hiddenDepth < 0) super.characters(ch, start, length);
+ }
+
+ @Override
+ public void ignorableWhitespace(char[] ch, int start, int length) throws SAXException {
+ if (hiddenDepth < 0) super.ignorableWhitespace(ch, start, length);
+ }
+
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/ElementSelectionFilter.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/ElementSelectionFilter.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/MergeContentFilter.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/MergeContentFilter.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/MergeContentFilter.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/MergeContentFilter.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,57 @@
+package aQute.libg.sax.filters;
+
+import java.util.Collections;
+import java.util.LinkedList;
+import java.util.List;
+
+import org.xml.sax.Attributes;
+import org.xml.sax.SAXException;
+
+import aQute.libg.sax.ContentFilterImpl;
+import aQute.libg.sax.SAXElement;
+
+public class MergeContentFilter extends ContentFilterImpl {
+
+ private int elementDepth = 0;
+
+ private final List<SAXElement> rootElements = new LinkedList<SAXElement>();
+
+ @Override
+ public void startElement(String uri, String localName, String qName, Attributes atts) throws SAXException {
+ if (elementDepth++ == 0) {
+ if (rootElements.isEmpty())
+ super.startElement(uri, localName, qName, atts);
+ else if (!rootElements.get(0).getqName().equals(qName))
+ throw new SAXException(String.format("Documents have inconsistent root element names: first was %s, current is %s.", rootElements.get(0).getqName(), qName));
+ rootElements.add(new SAXElement(uri, localName, qName, atts));
+ } else {
+ super.startElement(uri, localName, qName, atts);
+ }
+ }
+
+ @Override
+ public void endElement(String uri, String localName, String qName) throws SAXException {
+ if (--elementDepth > 0) {
+ super.endElement(uri, localName, qName);
+ }
+ }
+
+ @Override
+ public void processingInstruction(String target, String data) throws SAXException {
+ if (rootElements.isEmpty())
+ super.processingInstruction(target, data);
+ }
+
+ public void closeRootAndDocument() throws SAXException {
+ if (!rootElements.isEmpty()) {
+ SAXElement root = rootElements.get(0);
+ super.endElement(root.getUri(), root.getLocalName(), root.getqName());
+ }
+ super.endDocument();
+ }
+
+ public List<SAXElement> getRootElements() {
+ return Collections.unmodifiableList(rootElements);
+ }
+
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/MergeContentFilter.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/MergeContentFilter.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/filters/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
\ No newline at end of file
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/sax/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
\ No newline at end of file
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/Replacer.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/Replacer.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/Replacer.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/Replacer.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,5 @@
+package aQute.libg.sed;
+
+public interface Replacer {
+ String process(String line);
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/Replacer.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/Replacer.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/Sed.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/Sed.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/Sed.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/Sed.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,82 @@
+package aQute.libg.sed;
+
+import java.io.*;
+import java.util.*;
+import java.util.regex.*;
+
+public class Sed {
+ final File file;
+ final Replacer macro;
+ File output;
+
+ final Map<Pattern, String> replacements = new LinkedHashMap<Pattern, String>();
+
+ public Sed(Replacer macro, File file) {
+ assert file.isFile();
+ this.file = file;
+ this.macro = macro;
+ }
+
+ public void setOutput(File f) {
+ output = f;
+ }
+
+ public void replace(String pattern, String replacement) {
+ replacements.put(Pattern.compile(pattern), replacement);
+ }
+
+ public void doIt() throws IOException {
+ BufferedReader brdr = new BufferedReader(new FileReader(file));
+ File out;
+ if (output != null)
+ out = output;
+ else
+ out = new File(file.getAbsolutePath() + ".tmp");
+ File bak = new File(file.getAbsolutePath() + ".bak");
+ PrintWriter pw = new PrintWriter(new FileWriter(out));
+ try {
+ String line;
+ while ((line = brdr.readLine()) != null) {
+ for (Pattern p : replacements.keySet()) {
+ String replace = replacements.get(p);
+ Matcher m = p.matcher(line);
+
+ StringBuffer sb = new StringBuffer();
+ while (m.find()) {
+ String tmp = setReferences(m, replace);
+ tmp = macro.process(tmp);
+ m.appendReplacement(sb, Matcher.quoteReplacement(tmp));
+ }
+ m.appendTail(sb);
+
+ line = sb.toString();
+ }
+ pw.println(line);
+ }
+ pw.close();
+ if (output == null) {
+ file.renameTo(bak);
+ out.renameTo(file);
+ }
+ } finally {
+ brdr.close();
+ pw.close();
+ }
+ }
+
+ private String setReferences(Matcher m, String replace) {
+ StringBuilder sb = new StringBuilder();
+ for (int i = 0; i < replace.length(); i++) {
+ char c = replace.charAt(i);
+ if (c == '$' && i < replace.length() - 1
+ && Character.isDigit(replace.charAt(i + 1))) {
+ int n = replace.charAt(i + 1) - '0';
+ if ( n <= m.groupCount() )
+ sb.append(m.group(n));
+ i++;
+ } else
+ sb.append(c);
+ }
+ return sb.toString();
+ }
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/Sed.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/Sed.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/sed/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/tarjan/Tarjan.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/tarjan/Tarjan.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/tarjan/Tarjan.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/tarjan/Tarjan.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,108 @@
+package aQute.libg.tarjan;
+
+import static java.lang.Math.*;
+
+import java.util.*;
+
+public class Tarjan<T> {
+
+ public class Node {
+ final T name;
+ final List<Node> adjacent = new ArrayList<Node>();
+ int low = -1;
+ int index = -1;
+
+ public Node(T name) {
+ this.name = name;
+ }
+
+ public String toString() {
+ return name + "{" + index + "," + low + "}";
+ }
+ }
+
+ private int index = 0;
+ private List<Node> stack = new ArrayList<Node>();
+ private Set<Set<T>> scc = new HashSet<Set<T>>();
+ private Node root = new Node(null);
+
+
+// public ArrayList<ArrayList<Node>> tarjan(Node v, AdjacencyList list){
+// v.index = index;
+// v.lowlink = index;
+// index++;
+// stack.add(0, v);
+// for(Edge e : list.getAdjacent(v)){
+// Node n = e.to;
+// if(n.index == -1){
+// tarjan(n, list);
+// v.lowlink = Math.min(v.lowlink, n.lowlink);
+// }else if(stack.contains(n)){
+// v.lowlink = Math.min(v.lowlink, n.index);
+// }
+// }
+// if(v.lowlink == v.index){
+// Node n;
+// ArrayList<Node> component = new ArrayList<Node>();
+// do{
+// n = stack.remove(0);
+// component.add(n);
+// }while(n != v);
+// SCC.add(component);
+// }
+// return SCC;
+// }
+
+ void tarjan(Node v) {
+ v.index = index;
+ v.low = index;
+ index++;
+ stack.add(0, v);
+ for (Node n : v.adjacent) {
+ if (n.index == -1) {
+ // first time visit
+ tarjan(n);
+ v.low = min(v.low, n.low);
+ } else if (stack.contains(n)) {
+ v.low = min(v.low, n.index);
+ }
+ }
+
+ if (v!=root && v.low == v.index) {
+ Set<T> component = new HashSet<T>();
+ Node n;
+ do {
+ n = stack.remove(0);
+ component.add(n.name);
+ } while (n != v);
+ scc.add(component);
+ }
+ }
+
+ Set<Set<T>> getResult(Map<T, ? extends Collection<T>> graph) {
+ Map<T, Node> index = new HashMap<T, Node>();
+
+ for (Map.Entry<T, ? extends Collection<T>> entry : graph.entrySet()) {
+ Node node = getNode(index, entry.getKey());
+ root.adjacent.add(node);
+ for (T adj : entry.getValue())
+ node.adjacent.add(getNode(index, adj));
+ }
+ tarjan(root);
+ return scc;
+ }
+
+ private Node getNode(Map<T, Node> index, T key) {
+ Node node = index.get(key);
+ if (node == null) {
+ node = new Node(key);
+ index.put(key, node);
+ }
+ return node;
+ }
+
+ public static <T> Set<Set<T>> tarjan(Map<T, Set<T>> graph) {
+ Tarjan<T> tarjan = new Tarjan<T>();
+ return tarjan.getResult(graph);
+ }
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/tarjan/Tarjan.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/tarjan/Tarjan.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/tarjan/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/tarjan/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/tarjan/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/tarjan/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/tuple/Pair.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/tuple/Pair.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/tuple/Pair.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/tuple/Pair.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,11 @@
+package aQute.libg.tuple;
+
+public class Pair<A,B> {
+ final public A a;
+ final public B b;
+
+ public Pair(A a, B b) {
+ this.a = a;
+ this.b = b;
+ }
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/tuple/Pair.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/tuple/Pair.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/tuple/packageinfo
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/tuple/packageinfo?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/tuple/packageinfo (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/tuple/packageinfo Mon Oct 17 10:31:43 2011
@@ -0,0 +1 @@
+version 1.0
Added: felix/trunk/bundleplugin/src/main/java/aQute/libg/version/Version.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/aQute/libg/version/Version.java?rev=1185095&view=auto
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/aQute/libg/version/Version.java (added)
+++ felix/trunk/bundleplugin/src/main/java/aQute/libg/version/Version.java Mon Oct 17 10:31:43 2011
@@ -0,0 +1,148 @@
+package aQute.libg.version;
+
+import java.util.regex.*;
+
+public class Version implements Comparable<Version> {
+ final int major;
+ final int minor;
+ final int micro;
+ final String qualifier;
+ public final static String VERSION_STRING = "(\\d+)(\\.(\\d+)(\\.(\\d+)(\\.([-_\\da-zA-Z]+))?)?)?";
+ public final static Pattern VERSION = Pattern
+ .compile(VERSION_STRING);
+ public final static Version LOWEST = new Version();
+ public final static Version HIGHEST = new Version(Integer.MAX_VALUE,
+ Integer.MAX_VALUE,
+ Integer.MAX_VALUE,
+ "\uFFFF");
+
+ public Version() {
+ this(0);
+ }
+
+ public Version(int major, int minor, int micro, String qualifier) {
+ this.major = major;
+ this.minor = minor;
+ this.micro = micro;
+ this.qualifier = qualifier;
+ }
+
+ public Version(int major, int minor, int micro) {
+ this(major, minor, micro, null);
+ }
+
+ public Version(int major, int minor) {
+ this(major, minor, 0, null);
+ }
+
+ public Version(int major) {
+ this(major, 0, 0, null);
+ }
+
+ public Version(String version) {
+ Matcher m = VERSION.matcher(version);
+ if (!m.matches())
+ throw new IllegalArgumentException("Invalid syntax for version: "
+ + version);
+
+ major = Integer.parseInt(m.group(1));
+ if (m.group(3) != null)
+ minor = Integer.parseInt(m.group(3));
+ else
+ minor = 0;
+
+ if (m.group(5) != null)
+ micro = Integer.parseInt(m.group(5));
+ else
+ micro = 0;
+
+ qualifier = m.group(7);
+ }
+
+ public int getMajor() {
+ return major;
+ }
+
+ public int getMinor() {
+ return minor;
+ }
+
+ public int getMicro() {
+ return micro;
+ }
+
+ public String getQualifier() {
+ return qualifier;
+ }
+
+ public int compareTo(Version other) {
+ if (other == this)
+ return 0;
+
+ if (!(other instanceof Version))
+ throw new IllegalArgumentException(
+ "Can only compare versions to versions");
+
+ Version o = (Version) other;
+ if (major != o.major)
+ return major - o.major;
+
+ if (minor != o.minor)
+ return minor - o.minor;
+
+ if (micro != o.micro)
+ return micro - o.micro;
+
+ int c = 0;
+ if (qualifier != null)
+ c = 1;
+ if (o.qualifier != null)
+ c += 2;
+
+ switch (c) {
+ case 0:
+ return 0;
+ case 1:
+ return 1;
+ case 2:
+ return -1;
+ }
+ return qualifier.compareTo(o.qualifier);
+ }
+
+ public String toString() {
+ StringBuffer sb = new StringBuffer();
+ sb.append(major);
+ sb.append(".");
+ sb.append(minor);
+ sb.append(".");
+ sb.append(micro);
+ if (qualifier != null) {
+ sb.append(".");
+ sb.append(qualifier);
+ }
+ return sb.toString();
+ }
+
+ public boolean equals(Object ot) {
+ if ( ! (ot instanceof Version))
+ return false;
+
+ return compareTo((Version)ot) == 0;
+ }
+
+ public int hashCode() {
+ return major * 97 ^ minor * 13 ^ micro
+ + (qualifier == null ? 97 : qualifier.hashCode());
+ }
+
+ public int get(int i) {
+ switch(i) {
+ case 0 : return major;
+ case 1 : return minor;
+ case 2 : return micro;
+ default:
+ throw new IllegalArgumentException("Version can only get 0 (major), 1 (minor), or 2 (micro)");
+ }
+ }
+}
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/version/Version.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: felix/trunk/bundleplugin/src/main/java/aQute/libg/version/Version.java
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision