volatile 工厂模式 highcharts variant rxjs vue安装教程 jquery使用ajax mysql删除一列 mysql查询结果拼接 mysql配置远程连接 python集合 python断言assert实例 python3基础教程 python获取时间戳 java接口 javastringbuilder javaenum java多线程编程 java格式化日期 网站后台模板 win10长期服务版 din字体 winhex使用教程 脚本 maya2016教程 今日头条邀请码 扫微信二维码诈骗原理 苹果放大镜 cad视口旋转 脚本列表 movavi 脚本学习 平面设计软件下载 facetime要钱吗 谷歌地球怎么用不了 产品修图 cdr怎么导出图片 ae烟雾特效 su模型交错 sharepoint下载
当前位置: 首页 > 学习教程  > 编程语言

INSTALL_FAILED_ABORTED

2020/12/28 18:37:01 文章标签:

android 安装流程.报错 INSTALL_FAILED_ABORTED: Session was abandoned 网上查得到安装流程中 在安装最后会使用 getPackageManager().getPackageInstaller().abandonSession(mSessionId); 岂不知,这句话就是导致这个报错的元凶 正常流程中,不需要使用这句话.只有异常处理中才…

android 安装流程.报错
INSTALL_FAILED_ABORTED: Session was abandoned
网上查得到安装流程中 在安装最后会使用
getPackageManager().getPackageInstaller().abandonSession(mSessionId);
岂不知,这句话就是导致这个报错的元凶

正常流程中,不需要使用这句话.只有异常处理中才要用这句话

我们可以从源码中看一下:

client端
官方入口
frameworks/base/packages/PackageInstaller/src/com/android/packageinstaller/InstallInstalling.java


    /**
     * Send the package to the package installer and then register a event result observer that
     * will call {@link #launchFinishBasedOnResult(int, int, String)}
     */
    private final class InstallingAsyncTask extends AsyncTask<Void, Void,
            PackageInstaller.Session> {
        volatile boolean isDone;

        @Override
        protected PackageInstaller.Session doInBackground(Void... params) {
            PackageInstaller.Session session;
            try {
                session = getPackageManager().getPackageInstaller().openSession(mSessionId);
            } catch (IOException e) {
                synchronized (this) {
                    isDone = true;
                    notifyAll();
                }
                return null;
            }

            session.setStagingProgress(0);

            try {
                File file = new File(mPackageURI.getPath());

                try (InputStream in = new FileInputStream(file)) {
                    long sizeBytes = file.length();
                    try (OutputStream out = session
                            .openWrite("PackageInstaller", 0, sizeBytes)) {
                        byte[] buffer = new byte[1024 * 1024];
                        while (true) {
                            int numRead = in.read(buffer);

                            if (numRead == -1) {
                                session.fsync(out);
                                break;
                            }

                            if (isCancelled()) {
                                session.close();
                                break;
                            }

                            out.write(buffer, 0, numRead);
                            if (sizeBytes > 0) {
                                float fraction = ((float) numRead / (float) sizeBytes);
                                session.addProgress(fraction);
                            }
                        }
                    }
                }

                return session;
            } catch (IOException | SecurityException e) {
                Log.e(LOG_TAG, "Could not write package", e);

                session.close();

                return null;
            } finally {
                synchronized (this) {
                    isDone = true;
                    notifyAll();
                }
            }
        }

        @Override
        protected void onPostExecute(PackageInstaller.Session session) {
            if (session != null) {
                Intent broadcastIntent = new Intent(BROADCAST_ACTION);
                broadcastIntent.setFlags(Intent.FLAG_RECEIVER_FOREGROUND);
                broadcastIntent.setPackage(getPackageName());
                broadcastIntent.putExtra(EventResultPersister.EXTRA_ID, mInstallId);

                PendingIntent pendingIntent = PendingIntent.getBroadcast(
                        InstallInstalling.this,
                        mInstallId,
                        broadcastIntent,
                        PendingIntent.FLAG_UPDATE_CURRENT);

                session.commit(pendingIntent.getIntentSender());
                mCancelButton.setEnabled(false);
                setFinishOnTouchOutside(false);
            } else {
                getPackageManager().getPackageInstaller().abandonSession(mSessionId);

                if (!isCancelled()) {
                    launchFailure(PackageManager.INSTALL_FAILED_INVALID_APK, null);
                }
            }
        }
    }

frameworks/base/core/java/android/content/pm/PackageInstaller.java

 /**
         * Completely abandon this session, destroying all staged data and
         * rendering it invalid. Abandoned sessions will be reported to
         * {@link SessionCallback} listeners as failures. This is equivalent to
         * opening the session and calling {@link Session#abandon()}.
         * 完全放弃此会话,破坏所有暂存的数据并使之无效。 放弃的会话将作为失败报告给{@link 
         * SessionCallback}侦听器。 这等效于打开会话并调用{@link Session#abandon()}。
         */
        public void abandon() {
            try {
                mSession.abandon();
            } catch (RemoteException e) {
                throw e.rethrowFromSystemServer();
            }
        }

service端
真正执行的地方
frameworks/base/services/core/java/com/android/server/pm/PackageInstallerService.java
frameworks/base/services/core/java/com/android/server/pm/PackageInstallerSession.java

 @Override
    public void abandon() {
        if (hasParentSessionId()) {
            throw new IllegalStateException(
                    "Session " + sessionId + " is a child of multi-package session "
                            + mParentSessionId +  " and may not be abandoned directly.");
        }

        List<PackageInstallerSession> childSessions = getChildSessionsNotLocked();
        synchronized (mLock) {
            if (params.isStaged && mDestroyed) {
                // If a user abandons staged session in an unsafe state, then system will try to
                // abandon the destroyed staged session when it is safe on behalf of the user.
                assertCallerIsOwnerOrRootOrSystemLocked();
            } else {
                assertCallerIsOwnerOrRootLocked();
            }

            if (isStagedAndInTerminalState()) {
                // We keep the session in the database if it's in a finalized state. It will be
                // removed by PackageInstallerService when the last update time is old enough.
                // Also, in such cases cleanStageDir() has already been executed so no need to
                // do it now.
                return;
            }
            if (mCommitted && params.isStaged) {
                mDestroyed = true;
                if (!mStagingManager.abortCommittedSessionLocked(this)) {
                    // Do not clean up the staged session from system. It is not safe yet.
                    mCallback.onStagedSessionChanged(this);
                    return;
                }
                cleanStageDir(childSessions);
            }

            if (mRelinquished) {
                Slog.d(TAG, "Ignoring abandon after commit relinquished control");
                return;
            }
            destroyInternal();
        }
        dispatchSessionFinished(INSTALL_FAILED_ABORTED, "Session was abandoned", null);
    }

本文链接: http://www.dtmao.cc/news_show_550050.shtml

附件下载

相关教程

    暂无相关的数据...

共有条评论 网友评论

验证码: 看不清楚?