📄 javacodecompact.java
字号:
/* * JavaCodeCompact.java 1.53 02/09/27 SMI * * Copyright (c) 1997-1998 Sun Microsystems, Inc. All Rights Reserved. * * This software is the confidential and proprietary information of Sun * Microsystems, Inc. ("Confidential Information"). You shall not * disclose such Confidential Information and shall use it only in * accordance with the terms of the license agreement you entered into * with Sun. * * SUN MAKES NO REPRESENTATIONS OR WARRANTIES ABOUT THE SUITABILITY OF THE * SOFTWARE, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE * IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR * PURPOSE, OR NON-INFRINGEMENT. SUN SHALL NOT BE LIABLE FOR ANY DAMAGES * SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING OR DISTRIBUTING * THIS SOFTWARE OR ITS DERIVATIVES. * Use is subject to license terms. */import components.*;import vm.*;import runtime.*;import util.*;import jcc.*;import java.io.PrintStream;import java.io.FileOutputStream;import java.io.IOException;import java.io.File;import java.util.Enumeration;import java.util.Vector;import java.util.Hashtable;public class JavaCodeCompact extends LinkerUtil { int verbosity = 0; boolean fail = false; ConstantPool t = new ConstantPool(); ClassFileFinder searchPath; String firstFileName; String outName; Vector arrayClasses = new Vector(); boolean classDebug = false; boolean ROMout = true; boolean outSet = false; String archName = "EVM"; boolean archSet = false; boolean doShared = false; Vector romAttributes = new Vector(); ClassReader rdr; MemberLoader memberLoader; Hashtable headerDirs = new Hashtable(31); String stubDestName; boolean stubTraceMode = false; ClassnameFilterList nativeTypes = new ClassnameFilterList(); ClassnameFilterList extraHeaders = new ClassnameFilterList(); int maxSegmentSize = -1; private void fileFound( String fname ){ // currently, the only thing we do with file names // is make them into potential output file names. if ( firstFileName == null ) firstFileName = fname; } private void makeOutfileName(){ if ( outName != null ) return; // already done by -o option. if (firstFileName==null) firstFileName = "ROMjava.c"; int sepindex = firstFileName.lastIndexOf( File.separatorChar )+1; int suffindex = firstFileName.lastIndexOf( '.' ); if ( suffindex < 0 ) suffindex = firstFileName.length(); outName = firstFileName.substring( sepindex, suffindex) + (ROMout ? ".c" : ".mclass"); } private void readFile( String fileName, Vector classesProcessed ){ if ( rdr == null ){ rdr = new ClassReader( t, verbosity ); } try { if (fileName.endsWith(".zip") || fileName.endsWith(".jar")){ rdr.readZip( fileName, classesProcessed ); } else { rdr.readFile( fileName, classesProcessed ); fileFound( fileName ); } } catch ( IOException e ){ System.out.println(Localizer.getString("javacodecompact.could_not_read_file", fileName)); e.printStackTrace(); fail = true; } } private void loadMembers( String filename, Vector classlist ){ if ( memberLoader == null ){ if ( rdr == null ){ rdr = new ClassReader( t, verbosity ); } if ( searchPath == null ){ searchPath = new ClassFileFinder(); } memberLoader = new MemberLoader( rdr, searchPath ); } try { memberLoader.readFromFile( filename, classlist ); } catch ( IOException e ){ System.err.println("-memberlist "+filename); e.printStackTrace(); fail = true; } } /* * Iterate through the shared constant pool, looking for * class constants that cannot be resolved. Make a list * of their names, as java Strings */ public Vector unresolvedClassNames(){ Vector names = new Vector(); Enumeration symbols = t.getEnumeration(); while ( symbols.hasMoreElements() ){ Object o = symbols.nextElement(); if ( o instanceof ClassConstant ){ ClassConstant cc = (ClassConstant)o; if ( ! cc.isResolved() ){ names.addElement( cc.name.string ); cc.forget(); // so 'unresolved' doesn't stick. } } } Enumeration classes = ClassInfo.allClasses(); while ( classes.hasMoreElements() ){ ClassInfo c = (ClassInfo) classes.nextElement(); ConstantObject constants[] = c.constants; if ( constants == null ) continue; int nc = constants.length; for ( int i = 0 ; i < nc; i++ ){ if ( (constants[i] instanceof ClassConstant ) && ! constants[i].isResolved() ){ // // so far, entries in the names array are // unique. But because each class has a separate // interfaces array, the current candidate // may already be on it. Avoid adding it // a second time! // Also, don't put arrays on this list! ClassConstant intrf = (ClassConstant)constants[i]; String intname = intrf.name.string; if ( (intname.charAt(0) != Const.SIGC_ARRAY ) && ! names.contains( intname ) ) names.addElement( intname ); intrf.forget(); // so 'unresolved' doesn't stick. } } } return names; } Vector classesProcessed = new Vector(); int nclasses = 0; boolean buildTables = true; boolean quicken = true; boolean doClosure = false; boolean qlossless = false; private boolean processOptions( String clist[] ){ boolean success = true; for( int i = 0; i < clist.length; i++ ){ if ( clist[i].equals(/*NOI18N*/"-c") ){ doClosure = true; continue; } else if ( clist[i].equals(/*NOI18N*/"-t") ){ buildTables = true; continue; } else if ( clist[i].equals(/*NOI18N*/"-q") ){ quicken = true; continue; } else if ( clist[i].equals(/*NOI18N*/"-nt") ){ buildTables = false; continue; } else if ( clist[i].equals(/*NOI18N*/"-nq") ){ quicken = false; continue; } else if ( clist[i].equals(/*NOI18N*/"-qlossless") ){ buildTables = true; quicken = true; qlossless = true; continue; } else if ( clist[i].equals(/*NOI18N*/"-g") ){ classDebug = true; ClassInfo.classDebug = true; continue; } else if ( clist[i].equals(/*NOI18N*/"-imageAttribute") ){ romAttributes.addElement( clist[ ++i ] ); continue; } else if ( clist[i].equals(/*NOI18N*/"-v") ){ verbosity++; continue; } else if ( clist[i].equals(/*NOI18N*/"-r") ){ ROMout = false; continue; } else if ( clist[i].equals(/*NOI18N*/"-o") ){ outName = clist[ ++i ]; } else if ( clist[i].equals(/*NOI18N*/"-classpath") ){ if ( searchPath == null ) searchPath = new ClassFileFinder(); searchPath.addToSearchPath( clist[ ++i ] ); } else if ( clist[i].equals(/*NOI18N*/"-arch") ){ String archArg = clist[ ++i ]; archName = archArg.toUpperCase(); if ( archSet ){ System.err.println(Localizer.getString("javacodecompact.too_many_-arch_targetarchname_specifiers")); success = false; } archSet = true; continue; } else if (clist[i].equals(/*NOI18N*/"-s")){ doShared = true; } else if ( clist[i].equals("-memberlist") ){ loadMembers( clist[++i], classesProcessed ); } else if ( clist[i].equals("-headersDir") ){ String type = clist[++i]; String dir = clist[++i]; headerDirs.put(type, dir); buildTables = true; // got to. } else if ( clist[i].equals("-stubs") ){ stubDestName = clist[++i]; } else if ( clist[i].equals("-trace") ){ stubTraceMode = true; } else if ( clist[i].equals("-f") ){ try { success = processOptions( parseOptionFile( clist[++i] ) ); } catch ( java.io.IOException e ){ e.printStackTrace(); success = false; } } else if ( clist[i].equals("-nativesType") ){ String name = clist[++i]; String patterns = clist[++i]; nativeTypes.addTypePatterns( name, patterns ); } else if ( clist[i].equals("-extraHeaders") ){ String name = clist[++i]; String patterns = clist[++i]; extraHeaders.addTypePatterns( name, patterns ); } else if ( clist[i].equals("-maxSegmentSize") ){ String arg = clist[++i]; try { maxSegmentSize = (new Integer(arg)).intValue(); } catch (NumberFormatException ex) { System.err.println(Localizer.getString("javacodecompact.invalid_max_segment_size")); success = false; } } else { readFile( clist[i], classesProcessed ); } } // Default classname filter for natives nativeTypes.addTypePatterns( "JDKPack", "-*" ); return success; } public boolean process( String clist[] ){ if ( ! processOptions( clist ) ) return false; makeOutfileName(); if ( !ROMout ){ quicken = false; buildTables = false; } if ( doClosure ){ while ( !fail ){ Vector unresolved = unresolvedClassNames(); if ( unresolved.size() == 0 ) break; // none left! Enumeration ulist = unresolved.elements(); int nfound = 0; while ( ulist.hasMoreElements() ){ String uname = (String)ulist.nextElement(); nfound += rdr.readClass(uname, searchPath, classesProcessed); } if ( nfound == 0 ){ // the list now contains things which could // not ever be resolved. Print it out for // information and go on. // this is not actually an error! if ( verbosity > 0 ){ ulist = unresolved.elements(); System.out.println(Localizer.getString("javacodecompact.could_not_resolve_these_names")); while( ulist.hasMoreElements() ){ System.out.write('\t'); System.out.println( (String)ulist.nextElement() ); } } break; } } } if ( fail ){ return false; } if ( memberLoader != null ){ // then we saw a -memberlist option. // go through all classes, hacking away // all unmarked, unwanted elements. memberLoader.deleteUnwantedMembers( classesProcessed ); } nclasses = classesProcessed.size(); ClassInfo c[] = new ClassInfo[ nclasses ]; classesProcessed.copyInto( c ); if ( buildTables ){ if ( verbosity != 0 )System.out.println(Localizer.getString("javacodecompact.resolving_superclass_hierarchy") ); if ( ! ClassInfo.resolveSupers() ){ return false; // missing superclass is a fatal error. } for ( int i = 0; i < nclasses; i++ ){ if ( verbosity != 0 )System.out.println(Localizer.getString("javacodecompact.building_tables_for_class", c[i].className)); c[i].buildReferenceFieldtable( t ); c[i].buildReferenceMethodtable( t ); } } for ( int i = 0; i < nclasses; i++ ){ c[i].findReferences(); } //if ( fail ) System.exit(1); // now write the output if ( verbosity != 0 )System.out.println(Localizer.getString("javacodecompact.writing_output_file")); writeNativesHeaders( nativeTypes, c, nclasses ); writeNativesHeaders( extraHeaders, c, nclasses ); if ( stubDestName != null ){ writeCStubs( c, nclasses ); } if ( ROMout ){ return writeROMFile( outName, c, romAttributes ); } else { MultiClass out = new MultiClass( t, c, verbosity>1 ); out.writeMultiClass( outName ); } return !fail; } public static void main( String clist[] ){
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -