📄 installer.java
字号:
state.nextStep++; } /** * Download the JAR, make sure it is the correct size, make sure * the required attributes match the JAD's, and then store the * application. * * @exception IOException is thrown, if an I/O error occurs during * descriptor or jar file download * @exception InvalidJadException is thrown, if the descriptor file is not * properly formatted or does not contain the required */ private void installStep5() throws IOException, InvalidJadException { String jarUrl; String tempFilename; int bytesDownloaded; RandomAccessStream myStorage = null; byte[] manifest; ManifestProperties jarProps; String configuration; String temp; String profile; String storageRoot; DataOutputStream storageStream; // Save jar file to temp name; we need to do this to read the // manifest entry, but, don't want to overwrite an exisiting // application in case there are problems with the manifest jarUrl = state.jadProps.getProperty(JAR_URL_PROP); if (jarUrl == null || jarUrl.length() == 0) { postStatusBackToProvider(INVALID_JAD_MSG); throw new InvalidJadException(InvalidJadException.MISSING_JAR_URL); } tempFilename = File.getStorageRoot() + TMP_FILENAME; try { bytesDownloaded = downloadJAR(jarUrl, tempFilename); } catch (InvalidJadException ije) { if (ije.getReason() == InvalidJadException.UNAUTHORIZED) { state.exception = ije; return; } throw ije; } try { if (bytesDownloaded != state.expectedJarSize) { postStatusBackToProvider(JAR_SIZE_MISMATCH_MSG); throw new InvalidJadException(InvalidJadException.JAR_SIZE_MISMATCH); } myStorage = new RandomAccessStream(classSecurityDomain); /* * if the domain owner is null then we do not have to verify * the JAR */ if (state.domainOwner != null) { verifyJar(state.jadProps, myStorage, tempFilename); } // Create JAR Properties (From .jar file's MANIFEST try { manifest = JarReader.readJarEntry(classSecurityDomain, tempFilename, JAR_MANIFEST); } catch (IOException ioe) { postStatusBackToProvider(INVALID_JAR_MSG); throw new InvalidJadException(InvalidJadException.CORRUPT_JAR); } jarProps = new ManifestProperties(); jarProps.load(new ByteArrayInputStream(manifest)); configuration = jarProps.getProperty(CONFIGURATION_PROP); if (configuration == null || configuration.length() == 0) { postStatusBackToProvider(INVALID_JAR_MSG); throw new InvalidJadException( InvalidJadException.MISSING_CONFIGURATION); } // JAD overrides the manifest temp = state.jadProps.getProperty(CONFIGURATION_PROP); if (temp != null) { configuration = temp; } /* * Since there is only one version to support, do a simple compare * of a harded coded value, so this code will break in * later versions. In later versions the configuration file * should be read and parsed and compared to the parsed * application value. */ if (!configuration.equals("CLDC-1.0")) { postStatusBackToProvider(INCOMPATIBLE_MSG); throw new InvalidJadException( InvalidJadException.DEVICE_INCOMPATIBLE); } profile = jarProps.getProperty(PROFILE_PROP); if (profile == null || profile.length() == 0) { postStatusBackToProvider(INVALID_JAR_MSG); throw new InvalidJadException(InvalidJadException.MISSING_PROFILE); } // JAD overrides the manifest temp = state.jadProps.getProperty(PROFILE_PROP); if (temp != null) { profile = temp; } /* * Since there is only one version to support, do a simple compare * of a harded coded value, so this code will break in * later versions. In later versions the configuration file * should be read and parsed and compared to the parsed * application value. */ if (!profile.equals("MIDP-1.0")) { postStatusBackToProvider(INCOMPATIBLE_MSG); throw new InvalidJadException( InvalidJadException.DEVICE_INCOMPATIBLE); } // Check Manifest entries against .jad file if (!state.suiteName.equals( jarProps.getProperty(SUITE_NAME_PROP))) { postStatusBackToProvider(ATTRIBUTE_MISMATCH_MSG); throw new InvalidJadException( InvalidJadException.SUITE_NAME_MISMATCH); } if (!state.version.equals(jarProps.getProperty(VERSION_PROP))) { postStatusBackToProvider(ATTRIBUTE_MISMATCH_MSG); throw new InvalidJadException(InvalidJadException.VERSION_MISMATCH); } if (!state.vendor.equals(jarProps.getProperty(VENDOR_PROP))) { postStatusBackToProvider(ATTRIBUTE_MISMATCH_MSG); throw new InvalidJadException(InvalidJadException.VENDOR_MISMATCH); } storageRoot = File.getStorageRoot() + state.storageName; // make sure at least 1 second has passed while (System.currentTimeMillis() - state.startTime < 1000); synchronized (state) { // this is the point of no return, one last check if (state.stopInstallation) { postStatusBackToProvider(USER_CANCELLED_MSG); throw new IOException("stopped"); } if (listener != null) { listener.updateStatus(STORING_SUITE); } state.writingSuite = true; } } catch (Exception e) { state.file.delete(tempFilename); if (e instanceof IOException) { throw (IOException)e; } throw (RuntimeException)e; } try { state.file.rename(tempFilename, storageRoot + JAR_FILENAME); myStorage.connect(storageRoot + MANIFEST_FILENAME, RandomAccessStream.READ_WRITE_TRUNCATE); myStorage.writeBytes(manifest, 0, manifest.length); myStorage.disconnect(); // Save JAD, JAR & manifest files myStorage.connect(storageRoot + JAD_FILENAME, RandomAccessStream.READ_WRITE_TRUNCATE); myStorage.writeBytes(state.jad, 0, state.jad.length); myStorage.disconnect(); // convert the JAD URL to UTF8 and write it to storage myStorage.connect(storageRoot + JAD_URL_FILENAME, RandomAccessStream.READ_WRITE_TRUNCATE); storageStream = myStorage.openDataOutputStream(); storageStream.writeUTF(state.jadUrl); storageStream.close(); myStorage.disconnect(); if (state.jadEncoding != null) { // convert the JAD encoding to UTF8 and write it to storage myStorage.connect(storageRoot + JAD_ENCODING_FILENAME, RandomAccessStream.READ_WRITE_TRUNCATE); storageStream = myStorage.openDataOutputStream(); storageStream.writeUTF(state.jadEncoding); storageStream.close(); myStorage.disconnect(); } else if (state.file.exists(storageRoot + JAD_ENCODING_FILENAME)) { // erase the old encoding since we did not get new one state.file.delete(storageRoot + JAD_ENCODING_FILENAME); } // todo get the jad encoding and write to a file if (state.domainOwner != null) { // convert the domain owner to UTF8 and write it to storage myStorage.connect(storageRoot + DOMAIN_OWNER_FILENAME, RandomAccessStream.READ_WRITE_TRUNCATE); storageStream = myStorage.openDataOutputStream(); storageStream.writeUTF(state.domainOwner); storageStream.close(); myStorage.disconnect(); } addToSuiteList(state.storageName); state.nextStep++; try { postStatusBackToProvider(SUCCESS_MSG); } catch (RuntimeException re) { /* * The suite is successfully installed, but the post of the * status message failed. Do not let this failure prevent * the suite from being used. */ } return; } catch (Exception e) { try { myStorage.disconnect(); } catch (IOException ex) { // ignore } remove(state.storageName); if (e instanceof IOException) { throw (IOException)e; } throw (RuntimeException)e; } } /** * Download an application descriptor file from the given URL. * * @return a byte array representation of the file or null if not found. * * @exception IOException is thrown if any error prevents the download * of the JAD. */ private byte[] downloadJAD() throws IOException { String[] encoding = new String[1]; ByteArrayOutputStream bos = new ByteArrayOutputStream(MAX_DL_SIZE); String[] acceptableTypes = {JAD_MT}; String[] extraFieldKeys = new String[3]; String[] extraFieldValues = new String[3]; String locale; extraFieldKeys[0] = "User-Agent"; extraFieldValues[0] = "Profile/" + System.getProperty("microedition.profiles") + " Configuration/" + System.getProperty("microedition.configuration"); extraFieldKeys[1] = "Accept-Charset"; extraFieldValues[1] = "UTF-8, " + System.getProperty("microedition.encoding"); /* locale can be null */ locale = System.getProperty("microedition.locale"); if (locale != null) { extraFieldKeys[2] = "Accept-Language"; extraFieldValues[2] = locale; } downloadResource(state.jadUrl, extraFieldKeys, extraFieldValues, acceptableTypes, bos, encoding, InvalidJadException.JAD_SERVER_NOT_FOUND, InvalidJadException.JAD_NOT_FOUND, InvalidJadException.INVALID_JAD_TYPE); state.jadEncoding = encoding[0]; return bos.toByteArray(); } /** * Download an application archive file from the given URL into the * given file. Automatically handle re-trys. * * @param jarUrl the URL from which the JAR can be retrieved. * * @param filename name of the file to write. This file resides * in the storage area of the given application. * * @return size of the JAR * * @exception IOException is thrown if any error prevents the download * of the JAR. */ private int downloadJAR(String jarUrl, String filename) throws IOException { HttpUrl parsedUrl; String url; String[] acceptableTypes = {JAR_MT_1, JAR_MT_2}; int jarSize; RandomAccessStream jarOutputStream = null; OutputStream outputStream = null; parsedUrl = new HttpUrl(jarUrl); if (parsedUrl.authority == null && state.jadUrl != null) { // relative URL, add the JAD URL as the base try { parsedUrl.addBaseUrl(state.jadUrl); } catch (IOException e) { postStatusBackToProvider(INVALID_JAD_MSG); throw new InvalidJadException( InvalidJadException.JAR_SERVER_NOT_FOUND); } url = parsedUrl.toString(); } else { url = jarUrl; } jarOutputStream = new RandomAccessStream(classSecurityDomain); jarOutputStream.connect(filename, RandomAccessStream.READ_WRITE_TRUNCATE); outputStream = jarOutputStream.openOutputStream(); try { jarSize = downloadResource(url, null, null, acceptableTypes, outputStream, null, InvalidJadException.JAR_SERVER_NOT_FOUND, InvalidJadException.JAR_NOT_FOUND, InvalidJadException.INVALID_JAR_TYPE); return jarSize; } catch (InvalidJadException ije) { switch (ije.getReason()) { case InvalidJadException.JAR_SERVER_NOT_FOUND: case InvalidJadException.JAR_NOT_FOUND: postStatusBackToProvider(INVALID_JAD_MSG); break; case InvalidJadException.INVALID_JAR_TYPE: postStatusBackToProvider(INVALID_JAR_MSG); } throw ije; } finally { try { jarOutputStream.disconnect(); } catch (Exception e) { // ignore } } } /**
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -