Search in sources :

Example 1 with LockdowndServiceDescriptor

use of org.robovm.libimobiledevice.LockdowndServiceDescriptor in project robovm by robovm.

the class AppLauncher method installInternal.

private void installInternal() throws Exception {
    try (LockdowndClient lockdowndClient = new LockdowndClient(device, getClass().getSimpleName(), true)) {
        final LibIMobileDeviceException[] ex = new LibIMobileDeviceException[1];
        final CountDownLatch countDownLatch = new CountDownLatch(1);
        LockdowndServiceDescriptor instproxyService = lockdowndClient.startService(InstallationProxyClient.SERVICE_NAME);
        try (InstallationProxyClient instClient = new InstallationProxyClient(device, instproxyService)) {
            instClient.upgrade("/PublicStaging/" + localAppPath.getName(), new Options().packageType(localAppPath.isDirectory() ? PackageType.Developer : null), new StatusCallback() {

                @Override
                public void progress(String status, int percentComplete) {
                    if (installStatusCallback != null) {
                        installStatusCallback.progress(status, percentComplete);
                    } else {
                        log("[%3d%%] %s", 50 + percentComplete / 2, status);
                    }
                }

                @Override
                public void success() {
                    try {
                        if (installStatusCallback != null) {
                            installStatusCallback.success();
                        } else {
                            log("[100%%] Installation complete");
                        }
                    } finally {
                        countDownLatch.countDown();
                    }
                }

                @Override
                public void error(String message) {
                    try {
                        ex[0] = new LibIMobileDeviceException(message);
                        if (installStatusCallback != null) {
                            installStatusCallback.error(message);
                        } else {
                            log("Error: %s", message);
                        }
                    } finally {
                        countDownLatch.countDown();
                    }
                }
            });
            countDownLatch.await();
        }
        if (ex[0] != null) {
            throw ex[0];
        }
    }
}
Also used : LibIMobileDeviceException(org.robovm.libimobiledevice.LibIMobileDeviceException) Options(org.robovm.libimobiledevice.InstallationProxyClient.Options) LockdowndServiceDescriptor(org.robovm.libimobiledevice.LockdowndServiceDescriptor) InstallationProxyClient(org.robovm.libimobiledevice.InstallationProxyClient) StatusCallback(org.robovm.libimobiledevice.InstallationProxyClient.StatusCallback) NSString(com.dd.plist.NSString) CountDownLatch(java.util.concurrent.CountDownLatch) LockdowndClient(org.robovm.libimobiledevice.LockdowndClient)

Example 2 with LockdowndServiceDescriptor

use of org.robovm.libimobiledevice.LockdowndServiceDescriptor in project robovm by robovm.

the class AppLauncher method launchInternal.

private int launchInternal() throws Exception {
    install();
    int lockedRetriesLeft = launchOnLockedRetries;
    while (true) {
        IDeviceConnection conn = null;
        String appPath = null;
        try (LockdowndClient lockdowndClient = new LockdowndClient(device, getClass().getSimpleName(), true)) {
            appPath = getAppPath(lockdowndClient, appId);
            // E.g. 7.0.2
            String productVersion = lockdowndClient.getValue(null, "ProductVersion").toString();
            // E.g. 11B508
            String buildVersion = lockdowndClient.getValue(null, "BuildVersion").toString();
            if (appLauncherCallback != null) {
                appLauncherCallback.setAppLaunchInfo(new AppLauncherInfo(device, appPath, productVersion, buildVersion));
            }
            LockdowndServiceDescriptor debugService = null;
            try {
                debugService = lockdowndClient.startService(DEBUG_SERVER_SERVICE_NAME);
            } catch (LibIMobileDeviceException e) {
                if (e.getErrorCode() == LockdowndError.LOCKDOWN_E_INVALID_SERVICE.swigValue()) {
                    // This happens when the developer image hasn't been mounted.
                    // Mount and try again.
                    mountDeveloperImage(lockdowndClient);
                    debugService = lockdowndClient.startService(DEBUG_SERVER_SERVICE_NAME);
                } else {
                    throw e;
                }
            }
            conn = device.connect(debugService.getPort());
            log("Debug server port: " + debugService.getPort());
            if (localPort != -1) {
                String exe = ((NSDictionary) PropertyListParser.parse(new File(localAppPath, "Info.plist"))).objectForKey("CFBundleExecutable").toString();
                log("launchios \"" + new File(localAppPath, exe).getAbsolutePath() + "\" \"" + appPath + "\" " + localPort);
                StringBuilder argsString = new StringBuilder();
                for (String arg : args) {
                    if (argsString.length() > 0) {
                        argsString.append(' ');
                    }
                    argsString.append(arg);
                }
                log("process launch -- " + argsString);
            }
        }
        if (lockedRetriesLeft == launchOnLockedRetries) {
            // First try
            log("Remote app path: " + appPath);
            log("Launching app...");
        } else {
            log("Launching app (retry %d of %d)...", (launchOnLockedRetries - lockedRetriesLeft), launchOnLockedRetries);
        }
        try {
            // otherwise perform port forwarding and stdout piping
            if (localPort == -1) {
                return pipeStdOut(conn, appPath);
            } else {
                return forward(conn, appPath);
            }
        } catch (RuntimeException e) {
            if (!e.getMessage().contains("Locked") || lockedRetriesLeft == 0) {
                throw e;
            }
            lockedRetriesLeft--;
            log("Device locked. Retrying launch in %d seconds...", secondsBetweenLaunchOnLockedRetries);
            Thread.sleep(secondsBetweenLaunchOnLockedRetries * 1000);
        } finally {
            conn.dispose();
        }
    }
}
Also used : LibIMobileDeviceException(org.robovm.libimobiledevice.LibIMobileDeviceException) IDeviceConnection(org.robovm.libimobiledevice.IDeviceConnection) AppLauncherInfo(org.robovm.libimobiledevice.util.AppLauncherCallback.AppLauncherInfo) LockdowndServiceDescriptor(org.robovm.libimobiledevice.LockdowndServiceDescriptor) NSString(com.dd.plist.NSString) LockdowndClient(org.robovm.libimobiledevice.LockdowndClient) ZipFile(java.util.zip.ZipFile) File(java.io.File)

Example 3 with LockdowndServiceDescriptor

use of org.robovm.libimobiledevice.LockdowndServiceDescriptor in project robovm by robovm.

the class AppLauncher method getAppPath.

private String getAppPath(LockdowndClient lockdowndClient, String appId) throws IOException {
    LockdowndServiceDescriptor instService = lockdowndClient.startService(InstallationProxyClient.SERVICE_NAME);
    try (InstallationProxyClient instClient = new InstallationProxyClient(device, instService)) {
        NSArray apps = instClient.browse();
        for (int i = 0; i < apps.count(); i++) {
            NSDictionary appInfo = (NSDictionary) apps.objectAtIndex(i);
            NSString bundleId = (NSString) appInfo.objectForKey("CFBundleIdentifier");
            if (bundleId != null && appId.equals(bundleId.toString())) {
                NSString path = (NSString) appInfo.objectForKey("Path");
                NSDictionary entitlements = (NSDictionary) appInfo.objectForKey("Entitlements");
                if (entitlements == null || entitlements.objectForKey("get-task-allow") == null || !entitlements.objectForKey("get-task-allow").equals(new NSNumber(true))) {
                    throw new RuntimeException("App with id '" + appId + "' does not " + "have the 'get-task-allow' entitlement and cannot be debugged");
                }
                if (path == null) {
                    throw new RuntimeException("Path for app with id '" + appId + "' not found");
                }
                return path.toString();
            }
        }
        throw new RuntimeException("No app with id '" + appId + "' found on device");
    }
}
Also used : NSNumber(com.dd.plist.NSNumber) LockdowndServiceDescriptor(org.robovm.libimobiledevice.LockdowndServiceDescriptor) NSArray(com.dd.plist.NSArray) NSDictionary(com.dd.plist.NSDictionary) InstallationProxyClient(org.robovm.libimobiledevice.InstallationProxyClient) NSString(com.dd.plist.NSString)

Example 4 with LockdowndServiceDescriptor

use of org.robovm.libimobiledevice.LockdowndServiceDescriptor in project robovm by robovm.

the class AppLauncher method mountDeveloperImage.

private void mountDeveloperImage(LockdowndClient lockdowndClient) throws Exception {
    // Find the DeveloperDiskImage.dmg path that best matches the current device. Here's what
    // the paths look like:
    // Platforms/iPhoneOS.platform/DeviceSupport/5.0/DeveloperDiskImage.dmg
    // Platforms/iPhoneOS.platform/DeviceSupport/6.0/DeveloperDiskImage.dmg
    // Platforms/iPhoneOS.platform/DeviceSupport/6.1/DeveloperDiskImage.dmg
    // Platforms/iPhoneOS.platform/DeviceSupport/7.0/DeveloperDiskImage.dmg
    // Platforms/iPhoneOS.platform/DeviceSupport/7.0 (11A465)/DeveloperDiskImage.dmg
    // Platforms/iPhoneOS.platform/DeviceSupport/7.0.3 (11B508)/DeveloperDiskImage.dmg
    // E.g. 7.0.2
    String productVersion = lockdowndClient.getValue(null, "ProductVersion").toString();
    // E.g. 11B508
    String buildVersion = lockdowndClient.getValue(null, "BuildVersion").toString();
    File deviceSupport = new File(getXcodePath(), "Platforms/iPhoneOS.platform/DeviceSupport");
    log("Looking up developer disk image for iOS version %s (%s) in %s", productVersion, buildVersion, deviceSupport);
    File devImage = findDeveloperImage(deviceSupport, productVersion, buildVersion);
    File devImageSig = new File(devImage.getParentFile(), devImage.getName() + ".signature");
    byte[] devImageSigBytes = Files.readAllBytes(devImageSig.toPath());
    LockdowndServiceDescriptor mimService = lockdowndClient.startService(MobileImageMounterClient.SERVICE_NAME);
    try (MobileImageMounterClient mimClient = new MobileImageMounterClient(device, mimService)) {
        log("Copying developer disk image %s to device", devImage);
        int majorVersion = Integer.parseInt(getProductVersionParts(productVersion)[0]);
        if (majorVersion >= 7) {
            // Use new upload method
            mimClient.uploadImage(devImage, null, devImageSigBytes);
        } else {
            LockdowndServiceDescriptor afcService = lockdowndClient.startService(AfcClient.SERVICE_NAME);
            try (AfcClient afcClient = new AfcClient(device, afcService)) {
                afcClient.makeDirectory("/PublicStaging");
                afcClient.fileCopy(devImage, "/PublicStaging/staging.dimage");
            }
        }
        log("Mounting developer disk image");
        NSDictionary result = mimClient.mountImage("/PublicStaging/staging.dimage", devImageSigBytes, null);
        NSString status = (NSString) result.objectForKey("Status");
        if (status == null || !"Complete".equals(status.toString())) {
            throw new IOException("Failed to mount " + devImage.getAbsolutePath() + " on the device.");
        }
    }
}
Also used : AfcClient(org.robovm.libimobiledevice.AfcClient) LockdowndServiceDescriptor(org.robovm.libimobiledevice.LockdowndServiceDescriptor) MobileImageMounterClient(org.robovm.libimobiledevice.MobileImageMounterClient) NSDictionary(com.dd.plist.NSDictionary) NSString(com.dd.plist.NSString) InterruptedIOException(java.io.InterruptedIOException) IOException(java.io.IOException) ZipFile(java.util.zip.ZipFile) File(java.io.File) NSString(com.dd.plist.NSString)

Aggregations

NSString (com.dd.plist.NSString)4 LockdowndServiceDescriptor (org.robovm.libimobiledevice.LockdowndServiceDescriptor)4 NSDictionary (com.dd.plist.NSDictionary)2 File (java.io.File)2 ZipFile (java.util.zip.ZipFile)2 InstallationProxyClient (org.robovm.libimobiledevice.InstallationProxyClient)2 LibIMobileDeviceException (org.robovm.libimobiledevice.LibIMobileDeviceException)2 LockdowndClient (org.robovm.libimobiledevice.LockdowndClient)2 NSArray (com.dd.plist.NSArray)1 NSNumber (com.dd.plist.NSNumber)1 IOException (java.io.IOException)1 InterruptedIOException (java.io.InterruptedIOException)1 CountDownLatch (java.util.concurrent.CountDownLatch)1 AfcClient (org.robovm.libimobiledevice.AfcClient)1 IDeviceConnection (org.robovm.libimobiledevice.IDeviceConnection)1 Options (org.robovm.libimobiledevice.InstallationProxyClient.Options)1 StatusCallback (org.robovm.libimobiledevice.InstallationProxyClient.StatusCallback)1 MobileImageMounterClient (org.robovm.libimobiledevice.MobileImageMounterClient)1 AppLauncherInfo (org.robovm.libimobiledevice.util.AppLauncherCallback.AppLauncherInfo)1