Verifying Jar Signature

后端 未结 2 1667
你的背包
你的背包 2020-12-03 16:00

I\'m trying to programmatically verify that a jar file has not been obviously tampered with. I have 2 use cases I want to prevent. 1) Modifications of existing classes 2) ad

2条回答
  •  离开以前
    2020-12-03 16:16

    Using the example below, I obtained the expected result for a correctly signed JAR (true) and an altered JAR (false). One simple way to trigger the effect for testing is to change one of the digests listed in META-INF/MANIFEST.MF.

    Note that this approach ignores entries that are not listed in the manifest. Using jarsigner -verify reports, "This jar contains unsigned entries which have not been integrity-checked." After reading the stream completely, entry.getCodeSigners() may be used to determine if an entry has any signers.

    import java.io.IOException;
    import java.io.InputStream;
    import java.util.Enumeration;
    import java.util.jar.JarEntry;
    import java.util.jar.JarFile;
    
    /** @see http://stackoverflow.com/questions/5587656 */
    public class Verify {
    
        public static void main(String[] args) throws IOException {
            System.out.println(verify(new JarFile(args[0])));
        }
    
        private static boolean verify(JarFile jar) throws IOException {
            Enumeration entries = jar.entries();
            while (entries.hasMoreElements()) {
                JarEntry entry = entries.nextElement();
                try {
                    byte[] buffer = new byte[8192];
                    InputStream is = jar.getInputStream(entry);
                    while ((is.read(buffer, 0, buffer.length)) != -1) {
                        // We just read. This will throw a SecurityException
                        // if a signature/digest check fails.
                    }
                } catch (SecurityException se) {
                    return false;
                }
            }
            return true;
        }
    }
    

    Note: For JDK 8, its not enough to merely get the input stream. As in jarsigner, the stream must be read from, too. In the code above, a loop adapted from the jar signer source has been added after getting the input stream.

提交回复
热议问题